Tĩnh chỉ đọc vs const


1387

Tôi đã đọc xung quanh conststatic readonlycác lĩnh vực. Chúng tôi có một số lớp chỉ chứa các giá trị không đổi. Được sử dụng cho những thứ khác nhau xung quanh trong hệ thống của chúng tôi. Vì vậy, tôi tự hỏi nếu quan sát của tôi là chính xác:

Những loại giá trị không đổi này phải luôn luôn static readonlydành cho mọi thứ công khai? Và chỉ sử dụng constcho các giá trị nội bộ / được bảo vệ / riêng tư?

Bạn đề xuất món gì? Tôi thậm chí có thể không sử dụng static readonlycác trường, nhưng có thể sử dụng các thuộc tính có thể?


5
Đây là một trường hợp duy nhất rất thú vị mà tôi vừa tìm thấy có lợi static readonly: hãy thử sử dụng một const bên trong IEnumeratornó sẽ kích hoạt một lỗi không đáng tin cậy yield và bạn sẽ nhận được một "lỗi trình biên dịch nội bộ" đáng sợ . Tôi đã không kiểm tra mã bên ngoài Unity3D, nhưng tôi tin rằng đây là lỗi đơn hoặc .NET . Đây là một vấn đề c # tuy nhiên.
cregox


8
Một điểm khác biệt nữa là bạn có thể sử dụng chuỗi const trong một công tắc, nhưng không phải là chuỗi chỉ đọc tĩnh
flagg19

7
static readonlykhông thể được sử dụng trong switch-casecâu lệnh dưới dạng casebiến, constđược yêu cầu cho mục đích này.
Mostafiz Rahman

3
static readonlycũng không thể được sử dụng làm tham số thuộc tính
Dread Boy

Câu trả lời:


940

public static readonlycác lĩnh vực là một chút khác thường; public staticcác thuộc tính (chỉ có a get) sẽ phổ biến hơn (có thể được hỗ trợ bởi một private static readonlytrường).

constcác giá trị được ghi trực tiếp vào trang web cuộc gọi; đây là hai lưỡi:

  • Sẽ vô ích nếu giá trị được tìm nạp trong thời gian chạy, có lẽ từ cấu hình
  • Nếu bạn thay đổi giá trị của một const, bạn cần xây dựng lại tất cả các máy khách
  • nhưng nó có thể nhanh hơn, vì nó tránh được một cuộc gọi phương thức ...
  • ... mà đôi khi có thể đã được JIT nội tuyến

Nếu giá trị sẽ không bao giờ thay đổi, thì const là tốt - Zerovv tạo các hằng số hợp lý; p Ngoài ra, staticcác thuộc tính là phổ biến hơn.


13
Tại sao một tài sản trên một lĩnh vực? Nếu đó là một lớp bất biến, tôi thấy không có gì khác biệt.
Michael Hedgpeth

73
@Michael - lý do như mọi khi; nó che giấu việc thực hiện. Bạn có thể thấy (sau này) rằng bạn cần phải lười biếng tải, dựa trên cấu hình, mặt tiền hoặc bất cứ điều gì. Trong thực tế, một trong hai thường sẽ ổn thôi ...
Marc Gravell

42
@CoffeeAddict theo định nghĩa, hằng số không lấy giá trị từ tệp cấu hình; nó được đốt cháy theo nghĩa đen vào thời gian biên dịch. Cách duy nhất bạn có thể sử dụng hằng số trong thời gian chạy là thông qua sự phản chiếu trên các trường. Bất cứ khi nào bạn cố gắng sử dụng nó, trình biên dịch đã thay thế việc sử dụng liên tục của bạn để sử dụng theo nghĩa đen ; tức là nếu một phương thức trong mã của bạn sử dụng 6 hằng số và bạn kiểm tra nó như IL, sẽ không có đề cập đến bất kỳ tra cứu liên tục nào; các giá trị theo nghĩa đen sẽ được tải tại chỗ
Marc Gravell

37
@MarcGravell - THẬN TRỌNG: readonlycác trường không thể được sử dụng trong các câu lệnh switch / case, thay vào đó bạn cần chúng const.
Luciano

7
@didibus Thay đổi một trường thành một thuộc tính, trên thực tế, phá vỡ API. Một trường trong C # hoạt động hiệu quả như một biến, trong khi một thuộc tính trong C # là một trình trợ giúp cú pháp để viết phương thức getter và / hoặc phương thức setter. Sự khác biệt này rất quan trọng khi các hội đồng khác có liên quan. Nếu bạn thay đổi một trường thành một thuộc tính và các hội đồng khác phụ thuộc vào trường này, thì các hội đồng khác đó phải được biên dịch lại.
Stephen Booher

237

Tôi sẽ sử dụng static readonlynếu Người tiêu dùng ở trong một hội đồng khác. Có constNgười tiêu dùng trong hai hội đồng khác nhau là một cách hay để tự bắn vào chân mình .


5
Vì vậy, tôi nghĩ như một số người đã đề cập hoặc ám chỉ, có thể là khôn ngoan khi chỉ sử dụng const cho các giá trị thực sự là các hằng số nổi tiếng nếu chúng được công khai nếu không chúng nên được dành riêng cho phạm vi truy cập nội bộ, được bảo vệ hoặc riêng tư.
jpierson

1
@Dio Lý do nó vẫn tồn tại là vì nó không phải là vấn đề thường gặp - đó là điều cần lưu ý, nhưng khả năng tạo nội tuyến trên các ranh giới lắp ráp là một điều tốt cho hiệu suất. Đó thực sự chỉ là vấn đề thực sự hiểu rằng "hằng số" có nghĩa là "nó sẽ không bao giờ thay đổi".
Michael Stum

1
@MichaelStum Ok tôi không nên gọi nó là "một vấn đề". Trong dòng công việc của tôi, tôi có const và chia sẻ nó trên các hội đồng nhưng tôi biên dịch lại cho mỗi lần triển khai hoặc gửi mã. Tuy nhiên, thực tế này chắc chắn đáng để lưu ý về nó.
Dio Phụng

1
Vì vậy, nói chung, internal consthoặc public static readonlytùy thuộc vào tầm nhìn mong muốn.
Iiridayn

2
@Iiridayn Vâng, đó không phải là một cách nhìn tồi. Có một vài trường hợp cạnh cần xem xét (ví dụ: nếu sử dụng Reflection hoặc nếu cần một giá trị trên một thuộc tính) và có những cách sử dụng hợp lệ cho public const(ví dụ: bất kỳ phần nào của tiêu chuẩn. Bất cứ khi nào tôi làm việc với XML, đều có tập tin không gian tên với một loạt các public const string.) Nhưng nói chung, public constchỉ nên được sử dụng sau khi xem xét các hàm ý đúng.
Michael Stum

200

Một số điều liên quan cần lưu ý hơn:

const int a

  • phải được khởi tạo.
  • khởi tạo phải ở thời gian biên dịch .

chỉ đọc int a

  • có thể sử dụng một giá trị mặc định, mà không cần khởi tạo.
  • việc khởi tạo có thể được thực hiện trong thời gian chạy (Chỉnh sửa: chỉ trong hàm tạo).

39
trong ctorchỉ.
Amit Kumar Ghosh

1
Không chỉ trong hàm tạo mà cả trong phần khai báo ( docs.microsoft.com/en-us/dotnet/csharp/lingu-reference/ trộm ).
deChristo

176

Đây chỉ là một bổ sung cho các câu trả lời khác. Tôi sẽ không lặp lại chúng (bây giờ bốn năm sau).

Có những tình huống mà a constvà không phải là có ngữ nghĩa khác nhau. Ví dụ:

const int y = 42;

static void Main()
{
  short x = 42;
  Console.WriteLine(x.Equals(y));
}

in ra True, trong khi:

static readonly int y = 42;

static void Main()
{
  short x = 42;
  Console.WriteLine(x.Equals(y));
}

viết False.

Lý do là phương thức x.Equalsnày có hai quá tải, một lấy trong một short( System.Int16) và một lấy object( System.Object). Bây giờ câu hỏi là liệu một hoặc cả hai áp dụng với ylập luận của tôi .

Khi ylà một hằng số thời gian biên dịch (theo nghĩa đen), các consttrường hợp, điều quan trọng trở nên rằng có tồn tại một chuyển đổi ngầm từ int đến short với điều kiện intlà một hằng số, và với điều kiện biên dịch C # xác nhận rằng giá trị của nó nằm trong phạm vi của một short( đó 42là). Xem ẩn chuyển đổi biểu thức hằng trong Đặc tả ngôn ngữ C #. Vì vậy, cả hai quá tải phải được xem xét. Quá tải Equals(short)được ưa thích (bất kỳ shortlà một object, nhưng không phải tất cả objectshort). Vì vậy, yđược chuyển đổi thành short, và quá tải đó được sử dụng. Sau đó Equalsso sánh hai shortgiá trị giống hệt nhau, và điều đó mang lại true.

Khi ykhông phải là một hằng số, không có ngầm chuyển đổi từ intđể shorttồn tại. Đó là bởi vì nói chung một cái intcó thể quá lớn để phù hợp với một short. (Một chuyển đổi rõ ràng đã tồn tại, nhưng tôi không nói Equals((short)y), vì vậy điều đó không liên quan.) Chúng tôi thấy rằng chỉ có một quá tải được áp dụng, đó là một quá tải Equals(object). Vì vậy, yđược đóng hộp để object. Sau đó Equalssẽ so sánh a System.Int16với a System.Int32và vì các loại thời gian chạy thậm chí không đồng ý, điều đó sẽ mang lại false.

Chúng tôi kết luận rằng trong một số trường hợp (hiếm), việc thay đổi constthành viên loại thành static readonlytrường (hoặc theo cách khác, khi có thể) có thể thay đổi hành vi của chương trình.


17
Một bổ sung tốt cho câu trả lời được chấp nhận. Tôi muốn thêm rằng việc chuyển đổi đúng kiểu dữ liệu và các hướng dẫn tương tự khác (như thử bắt v.v.) phải là một yếu tố chính của các lập trình viên có kinh nghiệm và không để lại cho trình biên dịch. Tuy nhiên, tôi đã học được một cái gì đó mới từ đây. Cảm ơn bạn.
Uknight 17/10/13

Ồ, tôi đã lập trình trong C # trong một thời gian dài và tôi sẽ không bao giờ đoán được rằng một int int trong phạm vi ngắn có thể được chuyển đổi hoàn toàn thành ngắn. Tôi phải nói rằng đó là khá kỳ lạ. Tôi yêu C # nhưng những mâu thuẫn kỳ lạ này dường như không tăng thêm giá trị nhưng thêm rất nhiều năng lực não cần thiết để liên tục cân nhắc có thể gây khó chịu, đặc biệt là cho người mới bắt đầu.
Mike Marynowski

@MikeMarynowski Đúng vậy. Nhưng tôi nghĩ họ đã đưa ra quy tắc đó (trong số những lý do khác) để đưa ra tuyên bố short x = 42;hợp pháp. Bởi vì ở đó bạn có một int, cụ thể là nghĩa đen 42, được ngầm biến thành short x. Nhưng sau đó, họ có thể đã giới hạn điều này chỉ bằng chữ số; Tuy nhiên, họ đã chọn để cho phép cũng những thứ như short x = y;nơi yđược định nghĩa là const int y = 42;, và sau đó họ đã kết thúc với điều này.
Jeppe Stig Nielsen

88

Một điều cần lưu ý là const bị giới hạn ở các kiểu nguyên thủy / giá trị (ngoại lệ là các chuỗi)


30
Trên thực tế constcũng có thể được sử dụng cho các loại khác, ngoại trừ việc nó phải được khởi tạo thành null, điều này làm cho nó vô dụng :)
nawfal

6
ngoại lệ như trong System.Exception? :)
Memet Olsen

4
@nawfal Chính xác hơn, chỉ các loại giá trịconstcó thể được sử dụng, là sbyte, byte, short, ushort, int, uint, long, ulong, char, float, double, decimal, bool, cộng với bất kỳ enumloại. constkhông thể được sử dụng cho các loại giá trị khác, như DateTimehoặc TimeSpanhoặc BigInteger. Nó cũng không thể được sử dụng cho IntPtrcấu trúc (được coi là một loại "nguyên thủy"; một số loại nguyên thủy gây nhầm lẫn trong C #). Có constthể được sử dụng cho tất cả các loại tham chiếu . Nếu kiểu là string, bất kỳ giá trị chuỗi có thể được chỉ định. Nếu không, giá trị phải được null.
Jeppe Stig Nielsen

@JeppeStigNielsen - Gần đây tôi đã có một cuộc tranh luận với người phục vụ về điều này - ông chỉ ra rằng bạn có thể tạo ra bất cứ điều gì (loại giá trị và tham chiếu) constbằng cách sử dụng default. Đối với structcác loại, đó là một phiên bản với tất cả các thành viên được đặt thành các giá trị mặc định.
Wai Ha Lee

28

Chỉ đọc tĩnh : Giá trị có thể được thay đổi thông qua hàm statictạo khi chạy. Nhưng không thông qua chức năng thành viên.

Hằng số : Theo mặc định static. Giá trị không thể thay đổi từ bất cứ đâu (Ctor, Chức năng, thời gian chạy vv không có ở đâu).

Chỉ đọc : Giá trị có thể được thay đổi thông qua hàm tạo khi chạy. Nhưng không thông qua chức năng thành viên.

Bạn có thể xem repo của tôi: các loại thuộc tính C # .


1
Tin xấu ... liên kết bị hỏng!
Fer R


Đoạn trích hay Siam ভাই :)
Muhammad Ashikuzzaman

25

Các readonlytừ khóa khác với consttừ khóa. Một consttrường chỉ có thể được khởi tạo tại khai báo của trường. Một readonlytrường có thể được khởi tạo tại khai báo hoặc trong hàm tạo. Do đó, readonlycác trường có thể có các giá trị khác nhau tùy thuộc vào hàm tạo được sử dụng. Ngoài ra, trong khi một consttrường là hằng số thời gian biên dịch, readonlytrường có thể được sử dụng cho các hằng số thời gian chạy

Tài liệu tham khảo MSDN ngắn và rõ ràng tại đây


16

constreadonlytương tự nhau, nhưng chúng không hoàn toàn giống nhau.

Một constlĩnh vực là một hằng số thời gian biên dịch, có nghĩa là giá trị mà có thể được tính tại thời gian biên dịch. Một readonlytrường cho phép các kịch bản bổ sung trong đó một số mã phải được chạy trong khi xây dựng loại. Sau khi xây dựng, một readonlylĩnh vực không thể thay đổi.

Chẳng hạn, constcác thành viên có thể được sử dụng để xác định các thành viên như:

struct Test
{
    public const double Pi = 3.14;
    public const int Zero = 0;
}

Vì các giá trị như 3.14 và 0 là hằng số thời gian biên dịch. Tuy nhiên, hãy xem xét trường hợp bạn xác định một loại và muốn cung cấp một số phiên bản pre-fab của loại đó. Ví dụ, bạn có thể muốn xác định lớp Màu và cung cấp "hằng số" cho các màu phổ biến như Đen, Trắng, v.v. Không thể làm điều này với các thành viên const, vì phía bên tay phải không phải là hằng số thời gian biên dịch. Người ta có thể làm điều này với các thành viên tĩnh thông thường:

public class Color
{
    public static Color Black = new Color(0, 0, 0);
    public static Color White = new Color(255, 255, 255);
    public static Color Red   = new Color(255, 0, 0);
    public static Color Green = new Color(0, 255, 0);
    public static Color Blue  = new Color(0, 0, 255);
    private byte red, green, blue;

    public Color(byte r, byte g, byte b) => (red, green, blue) = (r, g, b);
}

Nhưng sau đó, không có gì để giữ một khách hàng của Color khỏi bị làm phiền với nó, có lẽ bằng cách hoán đổi các giá trị Đen và Trắng. Không cần phải nói, điều này sẽ gây ra sự bối rối cho các khách hàng khác của lớp Màu. Tính năng "chỉ đọc" giải quyết tình huống này.

Bằng cách đơn giản là giới thiệu readonlytừ khóa trong các khai báo, chúng tôi duy trì việc khởi tạo linh hoạt trong khi ngăn chặn mã máy khách khỏi bị lừa đảo.

public class Color
{
    public static readonly Color Black = new Color(0, 0, 0);
    public static readonly Color White = new Color(255, 255, 255);
    public static readonly Color Red   = new Color(255, 0, 0);
    public static readonly Color Green = new Color(0, 255, 0);
    public static readonly Color Blue  = new Color(0, 0, 255);
    private byte red, green, blue;

    public Color(byte r, byte g, byte b) => (red, green, blue) = (r, g, b);
}

Thật thú vị khi lưu ý rằng các thành viên const luôn tĩnh, trong khi một thành viên chỉ đọc có thể là tĩnh hoặc không, giống như một trường thông thường.

Có thể sử dụng một từ khóa duy nhất cho hai mục đích này, nhưng điều này dẫn đến các vấn đề về phiên bản hoặc vấn đề về hiệu suất. Giả sử trong một khoảnh khắc chúng tôi đã sử dụng một từ khóa duy nhất cho (const) này và một nhà phát triển đã viết:

public class A
{
    public static const C = 0;
}

và một nhà phát triển khác đã viết mã dựa trên A:

public class B
{
    static void Main() => Console.WriteLine(A.C);
}

Bây giờ, mã được tạo có thể dựa vào thực tế rằng AC là hằng số thời gian biên dịch không? Tức là, việc sử dụng AC có thể được thay thế bằng giá trị 0 không? Nếu bạn nói "có" với điều này, thì điều đó có nghĩa là nhà phát triển của A không thể thay đổi cách khởi tạo AC - điều này ràng buộc tay của nhà phát triển A mà không được phép.

Nếu bạn nói "không" với câu hỏi này thì việc tối ưu hóa quan trọng sẽ bị bỏ qua. Có lẽ tác giả của A tích cực rằng AC sẽ luôn bằng không. Việc sử dụng cả const và readonly cho phép nhà phát triển của A chỉ định ý định. Điều này làm cho hành vi phiên bản tốt hơn và hiệu suất tốt hơn.


12

Sở thích của tôi là sử dụng const bất cứ khi nào tôi có thể, như đã đề cập ở trên chỉ giới hạn ở các biểu thức nghĩa đen hoặc một cái gì đó không cần đánh giá.

Nếu tôi chống lại giới hạn đó, thì tôi sẽ chuyển sang trạng thái tĩnh chỉ đọc , với một cảnh báo. Tôi thường sẽ sử dụng một thuộc tính tĩnh công khai với một getter và một trường chỉ đọc tĩnh riêng tư như Marc đề cập ở đây .


7

Const: Const không là gì ngoài "hằng số", một biến trong đó giá trị không đổi nhưng tại thời gian biên dịch. Và nó là bắt buộc để gán một giá trị cho nó. Theo mặc định, một const là tĩnh và chúng ta không thể thay đổi giá trị của biến const trong toàn bộ chương trình.

Tĩnh ReadOnly: Giá trị của biến loại chỉ đọc tĩnh có thể được chỉ định trong thời gian chạy hoặc được gán tại thời gian biên dịch và thay đổi khi chạy. Nhưng giá trị của biến này chỉ có thể được thay đổi trong hàm tạo tĩnh. Và không thể thay đổi hơn nữa. Nó chỉ có thể thay đổi một lần khi chạy

Tham khảo: c-sharpc Corner


6

Trường chỉ đọc tĩnh là thuận lợi khi hiển thị cho các hội đồng khác một giá trị có thể thay đổi trong phiên bản mới hơn.

Ví dụ, giả sử lắp ráp Xhiển thị một hằng số như sau:

public const decimal ProgramVersion = 2.3;

Nếu Ytham chiếu lắp ráp Xvà sử dụng hằng số này, giá trị 2.3 sẽ được đưa vào lắp ráp Ykhi được biên dịch. Điều này có nghĩa là nếu Xsau đó được biên dịch lại với hằng số được đặt thành 2.4, Yvẫn sẽ sử dụng giá trị cũ là 2.3 cho đến khi Yđược biên dịch lại. Một trường chỉ đọc tĩnh tránh được vấn đề này.

Một cách khác để xem xét điều này là bất kỳ giá trị nào có thể thay đổi trong tương lai không phải là hằng số theo định nghĩa, và do đó không nên được biểu diễn dưới dạng một.


3

hăng sô:

  1. giá trị nên được đưa ra khi khai báo
  2. biên dịch thời gian không đổi

chỉ đọc:

  1. giá trị có thể được đưa ra khi khai báo hoặc trong thời gian chạy bằng cách sử dụng hàm tạo. Giá trị có thể thay đổi tùy thuộc vào hàm tạo được sử dụng.
  2. thời gian chạy không đổi

3

Const : các giá trị biến const phải được xác định cùng với khai báo và sau đó nó sẽ không thay đổi. const hoàn toàn tĩnh vì vậy mà không tạo cá thể lớp, chúng ta có thể truy cập chúng. cái này có giá trị tại thời gian biên dịch

ReadOnly : các giá trị biến chỉ đọc chúng ta có thể định nghĩa trong khi khai báo cũng như sử dụng hàm tạo khi chạy. các biến chỉ đọc không thể truy cập mà không có thể hiện của lớp.

Tĩnh readonly : các giá trị biến chỉ đọc tĩnh chúng ta có thể định nghĩa trong khi khai báo cũng như chỉ thông qua hàm tạo tĩnh chứ không phải với bất kỳ biến constructor.these nào khác mà chúng ta có thể truy cập mà không cần tạo cá thể lớp (Như biến tĩnh).

chỉ đọc tĩnh sẽ là lựa chọn tốt hơn nếu chúng ta phải sử dụng các biến trong các cụm khác nhau. Vui lòng kiểm tra chi tiết đầy đủ trong liên kết dưới đây

https://www.stum.de/2009/01/14/const-strings-a-very-convenient-way-to-shoot-yourself-in-the- feet /


Bạn có thể cho tôi biết lý do tại sao bạn downvote câu trả lời, vì vậy tôi có thể cập nhật bản thân mình cũng như ở đây.
dùng1756922

Không phải DV, nhưng có thể câu trả lời này không thực sự thêm bất cứ điều gì vào câu trả lời đã toàn diện ở đây.
Marc L.

thực vậy, hãy nhớ lại từ Java vào cuối những năm 90, chúng tôi đã có một dự án, nhiều người sản xuất các lọ khác nhau với các tệp lớp tương tác (tham chiếu lẫn nhau) và chuỗi const công cộng gặp sự cố phiên bản, vì chúng được sao chép xung quanh
George Birbilis

2

Có một sự khác biệt nhỏ giữa trường const và trường chỉ đọc tĩnh trong C # .Net

const phải được khởi tạo với giá trị tại thời gian biên dịch.

const theo mặc định là tĩnh và cần được khởi tạo với giá trị không đổi, không thể sửa đổi sau này. Nó không thể được sử dụng với tất cả các kiểu dữ liệu. Ví dụ: DateTime. Nó không thể được sử dụng với kiểu dữ liệu DateTime.

public const DateTime dt = DateTime.Today;  //throws compilation error
public const string Name = string.Empty;    //throws compilation error
public static readonly string Name = string.Empty; //No error, legal

chỉ đọc có thể được khai báo là tĩnh, nhưng không cần thiết. Không cần phải khởi tạo tại thời điểm khai báo. Giá trị của nó có thể được gán hoặc thay đổi bằng cách sử dụng hàm tạo một lần. Vì vậy, có khả năng thay đổi giá trị của trường chỉ đọc một lần (không quan trọng, nó có tĩnh hay không), điều này là không thể với const.


0

Các hằng số giống như tên ngụ ý, các trường không thay đổi và thường được xác định tĩnh tại thời gian biên dịch trong mã.

Các biến chỉ đọc là các trường có thể thay đổi trong các điều kiện cụ thể.

Chúng có thể được khởi tạo khi bạn lần đầu tiên khai báo chúng như một hằng số, nhưng thông thường chúng được khởi tạo trong quá trình xây dựng đối tượng bên trong hàm tạo.

Chúng không thể được thay đổi sau khi khởi tạo diễn ra, trong các điều kiện được đề cập ở trên.

Đối với tôi, chỉ đọc tĩnh có vẻ là một lựa chọn kém, nếu nó tĩnh và không bao giờ thay đổi, vì vậy chỉ cần sử dụng nó ở chế độ công khai, nếu nó có thể thay đổi thì đó không phải là hằng số và tùy theo nhu cầu của bạn, bạn có thể sử dụng đọc -only hoặc chỉ là một biến thông thường.

Ngoài ra, một sự khác biệt quan trọng khác là hằng số thuộc về lớp, trong khi biến chỉ đọc thuộc về thể hiện!


0

Một const (được xác định tại thời gian biên dịch) có thể được sử dụng trong trường hợp tĩnh không đọc được, như trong câu lệnh chuyển đổi hoặc hàm tạo thuộc tính. Điều này là do các trường chỉ đọc chỉ được giải quyết trong thời gian chạy và một số cấu trúc mã yêu cầu đảm bảo thời gian biên dịch. Một tĩnh chỉ đọc có thể được tính toán trong một hàm tạo, thường là một thứ thiết yếu và hữu ích. Sự khác biệt là chức năng, theo ý kiến ​​của tôi nên được sử dụng.

Về mặt phân bổ bộ nhớ, ít nhất là với các chuỗi (là một kiểu tham chiếu), dường như không có sự khác biệt nào trong đó cả hai đều được thực hiện và sẽ tham chiếu một thể hiện được thực hiện.

Cá nhân, mặc định của tôi là tĩnh chỉ đọc, vì nó có ý nghĩa ngữ nghĩa và logic hơn đối với tôi, đặc biệt là vì hầu hết các giá trị không cần thiết trong thời gian biên dịch. Và, nhân tiện, các thống kê chỉ đọc công khai không phải là bất thường hoặc không phổ biến như câu trả lời được đánh dấu: ví dụ, System.String.Emptylà một.


0

Một sự khác biệt khác giữa khai báo constchỉ đọc tĩnh là trong cấp phát bộ nhớ.

Một trường tĩnh thuộc về loại đối tượng chứ không phải là một thể hiện của loại đó. Kết quả là, một khi lớp được tham chiếu lần đầu tiên, trường tĩnh sẽ "sống" trong bộ nhớ trong thời gian còn lại và cùng một thể hiện của trường tĩnh sẽ được tham chiếu bởi tất cả các thể hiện của loại.

Mặt khác, trường const "thuộc về một thể hiện của loại.

Nếu bộ nhớ của sự phân chia là quan trọng hơn đối với bạn, thích sử dụng const . Nếu tốc độ, sau đó sử dụng tĩnh chỉ đọc .

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.