最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

淺談C# 中 const 與 readonly的核心區(qū)別

 更新時(shí)間:2026年05月10日 10:22:03   作者:bugcome_com  
在 C# 編程中,const?與?readonly?經(jīng)常被統(tǒng)稱為“常量”,但二者在初始化規(guī)則、編譯/運(yùn)行時(shí)行為、IL 生成方式、版本兼容性、引用類型語(yǔ)義等方面存在本質(zhì)差異,下面就來(lái)詳細(xì)的介紹一下,感興趣的可以了解一下

在 C# 編程中,const 與 readonly 經(jīng)常被統(tǒng)稱為“常量”,但二者在初始化規(guī)則、編譯/運(yùn)行時(shí)行為、IL 生成方式、版本兼容性、引用類型語(yǔ)義等方面存在本質(zhì)差異。誤用不僅可能引入隱蔽的邏輯錯(cuò)誤,還會(huì)帶來(lái)庫(kù)升級(jí)后的版本陷阱

一、初始化位置:編譯時(shí)強(qiáng)約束 vs 運(yùn)行時(shí)一次性賦值

1??const:必須聲明即賦值(編譯期確定)

  • 必須在聲明處賦值
  • 值在編譯階段就已確定
  • 任何位置都不能再次賦值(包括構(gòu)造函數(shù))
public class ConstantDemo
{
    public const int MaxRetryCount = 3;
    public const string DefaultTitle = "C#常量解析";

    // ? 編譯錯(cuò)誤:聲明時(shí)未賦值
    // public const double Pi;

    // ? 編譯錯(cuò)誤:不能在構(gòu)造函數(shù)中修改
    // public ConstantDemo()
    // {
    //     MaxRetryCount = 5;
    // }
}

?? 結(jié)論:const 是“聲明即終值”的編譯期常量

2??readonly:聲明時(shí)或構(gòu)造函數(shù)中賦值(運(yùn)行期確定)

  • 可以在聲明處賦值
  • 也可以在 實(shí)例構(gòu)造函數(shù) / 靜態(tài)構(gòu)造函數(shù) 中賦值
  • 每個(gè)字段只允許賦值一次
public class ReadonlyDemo
{
    // 聲明時(shí)賦值
    public readonly int MinAge = 18;

    // 構(gòu)造函數(shù)中賦值
    public readonly int UserId;
    public ReadonlyDemo(int userId)
    {
        UserId = userId;
    }

    // 靜態(tài) readonly:在靜態(tài)構(gòu)造函數(shù)中賦值
    public static readonly string Version;
    static ReadonlyDemo()
    {
        Version = "1.0.1";
    }
}

?? 結(jié)論:readonly 是“構(gòu)造期凍結(jié)”的運(yùn)行時(shí)常量。

二、修飾對(duì)象范圍:字段 + 局部變量 vs 僅字段

const:字段 & 局部變量都支持

public class ConstScopeDemo
{
    public const int GlobalConst = 100;

    public void LocalConstDemo()
    {
        const string LocalMsg = "局部常量";
        Console.WriteLine(LocalMsg);
    }
}

readonly:只能修飾字段

public class ReadonlyScopeDemo
{
    public readonly int FieldReadonly = 50;

    public void LocalReadonlyError()
    {
        // ? 編譯錯(cuò)誤:readonly 不能修飾局部變量
        // readonly int x = 10;
    }
}

三、編譯期 vs 運(yùn)行期:這是最本質(zhì)的差異 ???

1??const:值被直接“內(nèi)聯(lián)”到 IL 中

public const int ConstValue = 10;

public void UseConst()
{
    int a = ConstValue;
}

IL 行為本質(zhì)

ldc.i4.s 10   // 直接壓棧常量 10

?? 重大隱患(版本陷阱):

  • 修改類庫(kù)中的 const 值
  • 但 引用方未重新編譯
  • 引用方仍然使用舊值 ?

2??readonly:始終通過(guò)字段訪問(wèn)(運(yùn)行期綁定)

public readonly int ReadonlyValue;

public ReadonlyDemo()
{
    ReadonlyValue = 20;
}

public void UseReadonly()
{
    int b = ReadonlyValue;
}

IL 行為本質(zhì)

ldfld int32 ReadonlyValue

? 修改值后,只需重新編譯類庫(kù)即可,調(diào)用方無(wú)需重新編譯。

四、靜態(tài)語(yǔ)義:隱式靜態(tài) vs 顯式靜態(tài)

const:天然 static,且禁止顯式聲明

public class ConstStaticDemo
{
    public const int ConstStatic = 10;

    // ? 編譯錯(cuò)誤
    // public static const int Invalid = 20;
}

調(diào)用方式:

int x = ConstStaticDemo.ConstStatic;

readonly:默認(rèn)實(shí)例級(jí),靜態(tài)需顯式聲明

public class ReadonlyStaticDemo
{
    public readonly int InstanceReadonly = 100;
    public static readonly int StaticReadonly = 200;
}

五、引用類型語(yǔ)義:值不可變 vs 引用不可變

const:僅支持string/null

public class ConstReferenceDemo
{
    public const string ConstString = "Hello";
    public const object ConstNull = null;

    // ? 編譯錯(cuò)誤
    // public const List<int> ConstList = new List<int>();
}

原因:

  • const 需要 編譯期確定值
  • 除 string 外,引用對(duì)象無(wú)法編譯期確定

readonly:支持任意引用類型(但僅鎖引用)

public class ReadonlyReferenceDemo
{
    public readonly List<int> Numbers = new() { 1, 2, 3 };

    public void Modify()
    {
        Numbers.Add(4);   // ? 合法

        // ? 編譯錯(cuò)誤:不能重新賦值
        // Numbers = new List<int>();
    }
}

?? readonly ≠ 不可變對(duì)象

  • 鎖的是 引用地址
  • 不是對(duì)象內(nèi)容

六、完整對(duì)比速查表

維度constreadonly
初始化時(shí)機(jī)編譯期運(yùn)行期
賦值位置僅聲明處聲明 / 構(gòu)造函數(shù)
修飾對(duì)象字段 + 局部變量僅字段
靜態(tài)特性默認(rèn) static默認(rèn)實(shí)例級(jí)
IL 行為內(nèi)聯(lián)常量字段訪問(wèn)
引用類型string / null任意引用類型
版本安全? 易出問(wèn)題? 安全

七、工程化使用建議(非常重要)

? 優(yōu)先使用const的場(chǎng)景

  • 數(shù)學(xué)常量(PI、E
  • 永不變化的協(xié)議值、枚舉值
  • 不會(huì)被類庫(kù)外部依賴引用的內(nèi)部常量
public const int MaxDays = 7;

? 推薦使用readonly的場(chǎng)景(真實(shí)項(xiàng)目更常見)

  • 類庫(kù)對(duì)外暴露的“常量”
  • 配置讀取、構(gòu)造參數(shù)注入
  • 引用類型常量(集合、策略對(duì)象等)
public static readonly string ConnectionString;
static DbConfig()
{
    ConnectionString = LoadFromConfig();
}

八、一句話記憶法(面試 & 實(shí)戰(zhàn))

const 是“編譯期寫死的字面量”
readonly 是“構(gòu)造期凍結(jié)的字段”

結(jié)語(yǔ)

const 與 readonly 的差異,本質(zhì)并不在“能不能改”,而在于:

  • 值是在什么時(shí)候決定的?(編譯期 vs 運(yùn)行期)
  • 是否參與 IL 內(nèi)聯(lián)?
  • 是否影響程序集版本兼容?

在真實(shí)工程中:

?? 99% 對(duì)外暴露的“常量”,都應(yīng)該使用 readonly 而不是 const。

理解這一點(diǎn),你就已經(jīng)超過(guò)了大多數(shù)只停留在語(yǔ)法層面的 C# 開發(fā)者。

到此這篇關(guān)于淺談C# 中 const 與 readonly的核心區(qū)別的文章就介紹到這了,更多相關(guān)C# const readonly內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • C#連接Mysql實(shí)現(xiàn)增刪改查的操作

    C#連接Mysql實(shí)現(xiàn)增刪改查的操作

    在IT行業(yè)中,數(shù)據(jù)庫(kù)連接是應(yīng)用程序開發(fā)中的重要環(huán)節(jié),尤其是在使用C#進(jìn)行Windows或者Web應(yīng)用開發(fā)時(shí),經(jīng)常需要與各種數(shù)據(jù)庫(kù)進(jìn)行交互,其中就包括廣泛使用的MySQL,本篇將詳細(xì)講解如何使用C#語(yǔ)言來(lái)連接MySQL數(shù)據(jù)庫(kù),以實(shí)現(xiàn)數(shù)據(jù)的讀取、寫入和其他操作
    2024-09-09
  • C#基于時(shí)間輪調(diào)度實(shí)現(xiàn)延遲任務(wù)詳解

    C#基于時(shí)間輪調(diào)度實(shí)現(xiàn)延遲任務(wù)詳解

    在很多.net開發(fā)體系中開發(fā)者在面對(duì)調(diào)度作業(yè)需求的時(shí)候一般會(huì)選擇三方開源成熟的作業(yè)調(diào)度框架來(lái)滿足業(yè)務(wù)需求,但是有些時(shí)候可能我們只是需要一個(gè)簡(jiǎn)易的延遲任務(wù)。本文主要分享一個(gè)簡(jiǎn)易的基于時(shí)間輪調(diào)度的延遲任務(wù)實(shí)現(xiàn),需要的可以參考一下
    2022-12-12
  • C#版的 Escape() 和 Unescape() 函數(shù)分享

    C#版的 Escape() 和 Unescape() 函數(shù)分享

    從網(wǎng)上看到兩個(gè)方法, C# 版的 Escape() 和 Unescape(),收藏下。
    2011-05-05
  • C# 表達(dá)式樹Expression Trees的知識(shí)梳理

    C# 表達(dá)式樹Expression Trees的知識(shí)梳理

    本篇文章主要介紹了表達(dá)式樹 Expression Trees的基礎(chǔ)知識(shí):Lambda 表達(dá)式創(chuàng)建表達(dá)式樹;API 創(chuàng)建表達(dá)式樹;編譯表達(dá)式樹;執(zhí)行表達(dá)式樹;修改表達(dá)式樹等等,具有一定的參考價(jià)值,下面跟著小編一起來(lái)看下吧
    2017-01-01
  • C#使用ADO.Net部件來(lái)訪問(wèn)Access數(shù)據(jù)庫(kù)的方法

    C#使用ADO.Net部件來(lái)訪問(wèn)Access數(shù)據(jù)庫(kù)的方法

    數(shù)據(jù)庫(kù)的訪問(wèn)是所有編程語(yǔ)言中最重要的部分,C#提供了ADO.Net部件用于對(duì)數(shù)據(jù)庫(kù)進(jìn)行訪問(wèn)。本文從最簡(jiǎn)單易用的微軟Access數(shù)據(jù)庫(kù)入手討論在C#中對(duì)數(shù)據(jù)庫(kù)的訪問(wèn)。
    2015-09-09
  • C#實(shí)現(xiàn)打印與打印預(yù)覽功能的思路及代碼

    C#實(shí)現(xiàn)打印與打印預(yù)覽功能的思路及代碼

    這篇文章主要介紹了C#實(shí)現(xiàn)打印與打印預(yù)覽功能的思路及代碼,有需要的朋友可以參考一下
    2013-12-12
  • C# 定時(shí)器定時(shí)更新的簡(jiǎn)單實(shí)例

    C# 定時(shí)器定時(shí)更新的簡(jiǎn)單實(shí)例

    這篇文章主要介紹了C#中定時(shí)器定時(shí)更新的簡(jiǎn)單實(shí)例。需要的朋友可以過(guò)來(lái)參考下,希望對(duì)大家有所幫助
    2013-12-12
  • c# 幾種常見的加密方法的實(shí)現(xiàn)

    c# 幾種常見的加密方法的實(shí)現(xiàn)

    這篇文章主要介紹了c# 幾種常見的加密方法的實(shí)現(xiàn),幫助大家更好的理解和使用c#,感興趣的朋友可以了解下
    2020-12-12
  • C#中winform窗體實(shí)現(xiàn)注冊(cè)/登錄功能實(shí)例(DBHelper類)

    C#中winform窗體實(shí)現(xiàn)注冊(cè)/登錄功能實(shí)例(DBHelper類)

    在編寫項(xiàng)目時(shí),編寫了一部分關(guān)于登錄頁(yè)面的一些代碼,下面這篇文章主要給大家介紹了關(guān)于C#中winform窗體實(shí)現(xiàn)注冊(cè)/登錄功能(DBHelper類)的相關(guān)資料,文中通過(guò)圖文介紹的非常詳細(xì),需要的朋友可以參考下
    2023-06-06
  • 從C#程序中調(diào)用非受管DLLs的方法

    從C#程序中調(diào)用非受管DLLs的方法

    這篇文章主要介紹了從C#程序中調(diào)用非受管DLLs的方法,是非常實(shí)用的技巧,有助于深入理解Windows程序設(shè)計(jì),需要的朋友可以參考下
    2014-10-10

最新評(píng)論

上思县| 贞丰县| 九寨沟县| 嵊泗县| 黄冈市| 康保县| 施甸县| 翼城县| 望城县| 杂多县| 遂宁市| 松桃| 田东县| 中山市| 汤原县| 鹤山市| 都兰县| 依兰县| 阳城县| 万全县| 舟山市| 浙江省| 荔波县| 阿拉善右旗| 景东| 西乡县| 乌什县| 利川市| 定远县| 敦煌市| 灵山县| 绥棱县| 岳池县| 樟树市| 子长县| 会昌县| 万荣县| 十堰市| 鸡西市| 祁连县| 镇宁|