함수에 의해 수정 될 수 있도록 객체를 전달해야하는 함수를 만들고 있습니다. 차이점은 무엇입니까?
public void myFunction(ref MyClass someClass)
과
public void myFunction(out MyClass someClass)
어느 것을 사용해야하며 왜 그런가요?
답변
ref
함수에 들어가기 전에 객체가 초기화 out
되었음을 컴파일러에 알리고 함수 내부에서 객체가 초기화 될 것을 컴파일러에 지시합니다.
동안은 그래서 ref
두 가지 방법 인, out
아웃 전용입니다.
답변
ref
수정 수단 :
- 값이 이미 설정되어 있으며
- 메소드는이를 읽고 수정할 수 있습니다.
out
수정 수단 :
- 값이 설정되지 않고 설정 될 때까지 메소드가 읽을 수 없습니다 .
- 메소드 는 리턴하기 전에 설정 해야합니다 .
답변
Dom이 Peter의 칸막이에 TPS 보고서에 대한 메모에 대해 등장한다고 가정 해 봅시다.
Dom이 심판 주장이라면, 그는 메모 사본을 인쇄했을 것입니다.
Dom이 논쟁의 여지가 없다면, Peter는 그와 함께 가져갈 메모의 새 사본을 인쇄하게 할 것입니다.
답변
나는 설명을 위해 내 손을 시험해 볼 것이다.
가치 유형이 올바르게 작동하는 방식을 이해하고 있다고 생각합니까? 값 유형은 (int, long, struct 등)입니다. ref 명령없이 함수로 보내면 데이터가 복사 됩니다 . 함수에서 해당 데이터에 대한 모든 작업은 원본이 아닌 사본에만 영향을 미칩니다. ref 명령은 ACTUAL 데이터를 보내고 변경 사항은 함수 외부의 데이터에 영향을줍니다.
혼란스러운 부분, 참조 유형을 확인하십시오.
참조 유형을 만들 수 있습니다.
List<string> someobject = new List<string>()
someobject 를 새로 만들면 두 부분이 생성됩니다.
- someobject에 대한 데이터를 보유하는 메모리 블록입니다 .
- 해당 데이터 블록에 대한 참조 (포인터).
이제 당신이 ref없이 메소드 에 어떤 객체 를 보낼 때 데이터가 아닌 참조 포인터를 복사합니다 . 이제 당신은 이것을 가지고 있습니다 :
(outside method) reference1 => someobject
(inside method) reference2 => someobject
동일한 객체를 가리키는 두 개의 참조 reference2를 사용하여 일부 객체 의 속성을 수정하면 reference1이 가리키는 동일한 데이터에 영향을 미칩니다.
(inside method) reference2.Add("SomeString");
(outside method) reference1[0] == "SomeString" //this is true
reference2를 널 아웃하거나 새 데이터를 가리키면 reference1 또는 data1이 가리키는 데이터에 영향을 미치지 않습니다.
(inside method) reference2 = new List<string>();
(outside method) reference1 != null; reference1[0] == "SomeString" //this is true
The references are now pointing like this:
reference2 => new List<string>()
reference1 => someobject
이제 객체 에 대한 참조로 메소드 를 보내면 어떻게됩니까 ? 실제 기준 에 SomeObject의이 방법에 보내지. 따라서 이제 데이터에 대한 참조가 하나만 있습니다.
(outside method) reference1 => someobject;
(inside method) reference1 => someobject;
그러나 이것은 무엇을 의미합니까? 그것은 두 가지 주요한 것을 제외하고 ref가 아닌 객체를 보내는 것과 정확히 동일하게 작동합니다.
1) 메소드 내부의 참조를 무효화하면 메소드 외부의 참조를 무효화합니다.
(inside method) reference1 = null;
(outside method) reference1 == null; //true
2) 이제 완전히 다른 데이터 위치를 가리키는 참조를 지정할 수 있으며 함수 외부의 참조는 이제 새 데이터 위치를 가리 킵니다.
(inside method) reference1 = new List<string>();
(outside method) reference1.Count == 0; //this is true
답변
심판에 와 아웃 .
out
요구 사항에 적합한 곳이면 어디에서나 사용 하십시오.
답변
밖:
C #에서 메서드는 하나의 값만 반환 할 수 있습니다. 둘 이상의 값을 반환하려면 out 키워드를 사용할 수 있습니다. 출력 수정자는 참조 기준으로 반환됩니다. 가장 간단한 대답은 키워드 “out”을 사용하여 메소드에서 값을 얻는 것입니다.
- 호출 함수에서 값을 초기화 할 필요는 없습니다.
- 호출 된 함수에 값을 할당해야합니다. 그렇지 않으면 컴파일러에서 오류를보고합니다.
심판 :
C #에서는 int, float, double 등과 같은 값 형식을 메서드 매개 변수의 인수로 전달하면 값으로 전달됩니다. 따라서 매개 변수 값을 수정하면 메소드 호출의 인수에 영향을 미치지 않습니다. 그러나“ref”키워드로 매개 변수를 표시하면 실제 변수에 반영됩니다.
- 함수를 호출하기 전에 변수를 초기화해야합니다.
- 메소드의 ref 매개 변수에 값을 지정하지 않아도됩니다. 값을 변경하지 않으면 “ref”로 표시해야합니까?
답변
개 확장, 고양이 예. ref가있는 두 번째 메소드는 호출자가 참조하는 오브젝트를 변경합니다. 따라서 “고양이”!!!
public static void Foo()
{
MyClass myObject = new MyClass();
myObject.Name = "Dog";
Bar(myObject);
Console.WriteLine(myObject.Name); // Writes "Dog".
Bar(ref myObject);
Console.WriteLine(myObject.Name); // Writes "Cat".
}
public static void Bar(MyClass someObject)
{
MyClass myTempObject = new MyClass();
myTempObject.Name = "Cat";
someObject = myTempObject;
}
public static void Bar(ref MyClass someObject)
{
MyClass myTempObject = new MyClass();
myTempObject.Name = "Cat";
someObject = myTempObject;
}