C #에서 필드를 '읽기 전용'으로 표시하면 어떤 이점이 있습니까?
멤버 변수를 읽기 전용으로 선언하면 어떤 이점이 있습니까? 클래스의 수명주기 동안 변화하는 누군가를 막 거나이 키워드로 인해 컴파일러 속도가 향상됩니까?
readonly
키워드는 런타임에서 산출되는 값을 멤버 변수 상수를 선언하는 데 사용하지만, 허용된다. 이것은 const
수정 자 (modifier)로 선언 된 상수와 다르며 , 컴파일시 값을 설정해야합니다. 를 사용 readonly
하면 선언 또는 필드가 속한 객체의 생성자에서 필드 값을 설정할 수 있습니다.
상수를 참조하는 외부 DLL을 다시 컴파일하지 않으려는 경우에도 사용하십시오 (컴파일 시간에 대체되기 때문에).
읽기 전용 필드를 사용하면 성능이 향상되지 않는다고 생각합니다. 객체가 완전히 구성되면 해당 필드가 새로운 값을 가리킬 수 없는지 확인하는 것입니다.
그러나 "읽기 전용"은 런타임에 CLR에 의해 시행되므로 다른 유형의 읽기 전용 의미론과는 매우 다릅니다. readonly 키워드는 CLR에서 확인할 수있는 .initonly로 컴파일됩니다.
이 키워드의 실제 장점은 변경 불가능한 데이터 구조를 생성하는 것입니다. 정의에 의한 불변 데이터 구조는 일단 생성 된 후에는 변경할 수 없습니다. 이를 통해 런타임시 구조의 동작을 쉽게 추론 할 수 있습니다. 예를 들어, 불변 구조를 코드의 다른 임의의 부분으로 전달할 위험이 없습니다. 그들은 그것을 바꿀 수 없으므로 그 구조에 대해 안정적으로 프로그래밍 할 수 있습니다.
다음은 불변성의 이점 중 하나에 대한 좋은 항목입니다. 스레딩
를 사용 readonly
하면 성능상의 이점이 없으며 적어도 어느 곳에서도 언급 한 적이 없습니다. 그것은 일단 초기화되면 수정을 방지하기 위해 당신이 제안한대로 정확하게하기위한 것입니다.
따라서보다 강력하고 읽기 쉬운 코드를 작성하는 데 도움이됩니다. 이와 같은 것의 실질적인 이점은 팀에서 일하거나 유지 보수를 할 때 발생합니다. readonly
코드에서 해당 변수의 사용에 대한 계약을 맺는 것과 비슷한 것을 선언 합니다. 다른 같은 키워드와 같은 방법으로 문서를 추가로 생각 internal
하거나 private
, 당신은 "이 변수가 초기화 후 수정할 수 없습니다"라고하고 있으며, 또한 당신이있어 시행 을.
따라서 클래스를 만들고 readonly
의도적으로 일부 멤버 변수 를 표시 하면 나중에 자신이나 다른 팀 멤버가 클래스를 확장하거나 클래스를 수정할 때 실수를 저지르는 것을 방지 할 수 있습니다. 내 의견으로는, 그것은 가치가있는 이점입니다 (댓글에서 doofledorfer가 언급 한 것처럼 추가 언어 복잡성으로 적은 비용으로).
매우 실용적인 용어로 말하면 :
dll A의 const를 사용하고 dll B가 그 const를 참조하면 해당 const의 값은 dll B로 컴파일됩니다. dll A를 해당 const의 새 값으로 재배치하면 dll B는 여전히 원래 값을 사용합니다.
읽기 전용 인 dll A 및 dll B 참조에서 읽기 전용을 사용하는 경우 해당 읽기 전용은 항상 런타임에 조회됩니다. 이는 dll A를 해당 읽기 전용의 새 값으로 재배치하면 dll B가 해당 새 값을 사용한다는 의미입니다.
컴파일러가 읽기 전용 키워드의 존재 여부에 따라 성능을 최적화 할 수있는 경우가 있습니다.
읽기 전용 필드도 static으로 표시된 경우에만 적용됩니다 . 이 경우 JIT 컴파일러는이 정적 필드가 절대 변경되지 않는다고 가정 할 수 있습니다. JIT 컴파일러는 클래스의 메소드를 컴파일 할 때이를 고려할 수 있습니다.
일반적인 예 : 클래스 에는 생성자에서 초기화 되는 정적 읽기 전용 IsDebugLoggingEnabled 필드가 있을 수 있습니다 (예 : 구성 파일 기반). 실제 메소드가 JIT 컴파일되면 디버그 로깅이 사용 가능하지 않은 경우 컴파일러가 코드의 전체 부분을 생략 할 수 있습니다.
이 최적화가 실제로 현재 버전의 JIT 컴파일러에서 구현되는지 확인하지 않았으므로 이것은 단지 추측입니다.
읽기 전용은 값 자체에만 적용되므로 참조 유형을 사용하는 경우 읽기 전용은 참조가 변경되지 않도록 보호합니다. 인스턴스의 상태는 읽기 전용으로 보호되지 않습니다.
params를 readonly
사용하여 생성자 외부 에서 필드를 설정 하는 해결 방법이 있다는 것을 잊지 마십시오 out
.
조금 지저분하지만 :
private readonly int _someNumber;
private readonly string _someText;
public MyClass(int someNumber) : this(data, null)
{ }
public MyClass(int someNumber, string someText)
{
Initialise(out _someNumber, someNumber, out _someText, someText);
}
private void Initialise(out int _someNumber, int someNumber, out string _someText, string someText)
{
//some logic
}
여기에 대한 추가 토론 : http://www.adamjamesnaylor.com/2013/01/23/Setting-Readonly-Fields-From-Chained-Constructors.aspx
사전 정의 또는 사전 계산 된 값이 프로그램 전체에서 동일하게 유지되어야하는 경우 상수를 사용해야하지만 런타임에 제공해야하는 값이 있지만 한 번 할당 된 값은 프로그램 전체에서 동일하게 유지되어야합니다. 읽기 전용. 예를 들어 프로그램 시작 시간을 할당해야하거나 사용자가 제공 한 값을 객체 초기화시 저장해야하며 추가 변경을 제한해야하는 경우 읽기 전용을 사용해야합니다.
이 질문에 대답하기 위해 기본 측면 추가 :
set
연산자 를 생략하면 속성을 읽기 전용으로 표현할 수 있습니다 . 따라서 대부분의 경우 readonly
키워드를 속성 에 추가 할 필요가 없습니다 .
public int Foo { get; } // a readonly property
이와 대조적으로 : readonly
유사한 효과를 얻으려면 필드에 키워드가 필요합니다 .
public readonly int Foo; // a readonly field
따라서 어떤 이유로 든 원하는 경우 필드를 속성으로 변경할 필요 readonly
없이 set
연산자없이 속성과 유사한 쓰기 방지 수준을 얻을 수있는 것처럼 필드를 표시하는 이점 이 있습니다.
전용 읽기 전용 배열에주의하십시오. 이것들이 클라이언트로 객체로 노출되면 (내가했던 것처럼 COM interop에 대해이 작업을 수행 할 수 있음) 클라이언트는 배열 값을 조작 할 수 있습니다. 배열을 객체로 반환 할 때는 Clone () 메서드를 사용하십시오.
readonly
선언시 초기화되거나 생성자에서만 값을 얻을 수 있습니다. 달리 const
초기화하고 동시에 선언해야합니다. readonly
모든 것이 const
있고 생성자 초기화
using System;
class MainClass {
public static void Main (string[] args) {
Console.WriteLine(new Test().c);
Console.WriteLine(new Test("Constructor").c);
Console.WriteLine(new Test().ChangeC()); //Error A readonly field
// `MainClass.Test.c' cannot be assigned to (except in a constructor or a
// variable initializer)
}
public class Test {
public readonly string c = "Hello World";
public Test() {
}
public Test(string val) {
c = val;
}
public string ChangeC() {
c = "Method";
return c ;
}
}
}
놀랍게도 Jon Skeet이 Noda Time 라이브러리를 테스트 할 때 발견 한 것처럼 읽기 전용은 실제로 코드 속도가 느려질 수 있습니다. 이 경우 20 초 동안 실행 된 테스트는 읽기 전용을 제거한 후 4 초 밖에 걸리지 않았습니다.
값 비싼 DependencyProperties가 필요 없으므로 WPF의 성능 이점이 있습니다. 이것은 컬렉션에 특히 유용 할 수 있습니다
읽기 전용 마킹 사용의 또 다른 흥미로운 부분은 싱글 톤에서 필드가 초기화되지 않도록 보호하는 것입니다.
예를 들어 csharpindepth의 코드에서 :
public sealed class Singleton
{
private static readonly Lazy<Singleton> lazy =
new Lazy<Singleton>(() => new Singleton());
public static Singleton Instance { get { return lazy.Value; } }
private Singleton()
{
}
}
readonly는 Singleton 필드가 두 번 초기화되지 않도록 보호하는 작은 역할을합니다. 또 다른 세부 사항은 언급 된 시나리오의 경우 const가 컴파일 시간 동안 작성을 강제하기 때문에 const를 사용할 수 없지만 singleton은 런타임에 작성한다는 것입니다.
참고 URL : https://stackoverflow.com/questions/277010/what-are-the-benefits-to-marking-a-field-as-readonly-in-c
'IT' 카테고리의 다른 글
* args와 ** kwargs는 무엇을 의미합니까? (0) | 2020.03.29 |
---|---|
WiX 트릭과 팁 (0) | 2020.03.29 |
스칼라에서 루프를 끊으려면 어떻게해야합니까? (0) | 2020.03.29 |
데이터를 복사하지 않고 Oracle 테이블의 복사본을 만들려면 어떻게해야합니까? (0) | 2020.03.29 |
Sublime Text 3의 80 자 / 오른쪽 여백 줄 (0) | 2020.03.29 |