2012-02-21 2 views
-1

X와 Y 좌표가있는 Point 구조체가 있다고 가정 해 보겠습니다. 이제 생성자가 있습니다 : Point (int x, int y).구조체 - 가능한 한 가장 빠른 값 변경

질문 : Point.SetXY (int x, int y)라는 메서드를 추가해야합니까?

예 : 내가 유 해달라고 때문에 빨리 알고 클래스에 대한

// I have some point 
point = new Point (5,5); 

// and I wanna change some values 
point = new Point (7,7); 

// or maybe should I do like this? 
point.SetXY (7,7); // is it faster? 

하지만 어쩌면 구조체 것이 문제가 나던 등 힙에 새 인스턴스를 만들 필요가?

+1

귀하의 벤치 마크에서 말하는 속도는 더 빠릅니까? –

+0

아직 벤치 마크를 사용하는 방법을 모르겠습니다. 한 번에 모든 것을 배울 수는 없습니다. – zgnilec

+1

신청서에 차이가 있다고 생각하는 이유가 있습니까? 너무 조기에 최적화 된 것처럼 들립니다. –

답변

2

Ithink 당신이

point.X = 7; 
point.Y = 7; 

하여 달성 할 수있는이 노출 필드

+0

그러나 그것은 매우 잘못되었습니다. – SLaks

+0

나는 이것이 가장 빠르다는 것을 알고 있지만, 나는 그것을 설정하기 위해 1 줄의 코드를 사용한다. – zgnilec

+0

이제 두 가지 스타일이 같음, 설정 스타일 및 생성자 스타일을 2000,000,000 회 반복 = 17 초 동안 테스트했습니다. X 및 Y에 직접 액세스하는 스타일 = 5 초이므로 가장 좋은 답변입니다. 고맙습니다. – zgnilec

4

아주 좋은 이유가 없다면 구조체를 변경하지 말 것을 제안합니다. 필요할 경우 새로운 X 및 Y 값으로 구조체를 만듭니다.

변경할 수있는 구조체가 반 직관적 인 이유에 대한 예는 (또는 evil (광고 라이선스에 관련된 측정 항목에 따라 다름)) Eric Lippert는 주제에 a very good blog post입니다.

+0

저는 구조체를 사용하고 있습니다. 저는 'Bullet'클래스 (예)를 가지고 있는데,이 클래스 안에는 'Point position'이 있습니다; 그래서 저는 제 안전하다고 생각합니다. 왜냐하면 alwyas가 수업을 통해이 분야를 거론하기 때문입니다. – zgnilec

+0

그 블로그 포스트는 메소드가 'this'를 변형시키는 구조체를 다루고 있습니다. 실제로는 문제가 될 수 있습니다. 어떤 사람들은'이'mutating 구조체가 문제가 있다는 사실, 또는 구조체가 필드를 노출 시켰을 때 초기의 컴파일러가 가변적 인 구조체에 대한 논점으로 바보 같은 코드를 생성 할 수 있다고 생각하는 것 같습니다. 그러나 나는 단지 그것을 보지 못합니다. . – supercat

1

구조체를 가장 빠른 악하지 않은 것입니다. 일부 정말 오래된 컴파일러와 같은 코드를 받아 들일 때 :

 
List<Point> myList; 
myList[4].X = 5; 

으로 myList [4] 임시 구조체에, 멀리 수정 된 구조체를 던져 구조체는 불변하고 그 일시 구조체의 필드 X를 수정, 복사 것이다 컴파일러가 위 구조에서 스 쿼크 할 수있게하는 방법이었습니다. 컴파일러가 이러한 코드에서 스 쿼크하는 것을 보장하는 더 좋은 방법은 컴파일러를 변경하여 임시 구조의 필드에 쓰기를 금지하는 것입니다. 그러한 코드가 오랫동안 컴파일러에 의해 금지되었다는 것을 감안할 때, 노출 된 필드를 가진 구조체는 종종 고정 된 수의 독립적 인 데이터 항목 (예 : 점, 사각형 등)을 보유하는 가장 좋은 방법입니다 (예 : 점, 사각형 등)

무엇이 문제인가? 생성자 또는 속성 설정자 이외의 함수가 this을 수정하는 구조체입니다. 컴파일러는 에 대한 쓰기가 someStructProperty을 수정하려고 시도하는 것을 인식하고 그러한 수정이 실제로 작동하지 않는 경우 컴파일러가이를 금지하므로 컴파일러는 someStructProperty.MutatingFunction()이 임시 인스턴스를 수정하려고 시도한다는 것을 알 수 없습니다. 구조체. 컴파일러는 실제로 의도 한대로 작동하지 않을지라도 그러한 코드를 허용합니다. 함수가 "제자리에서"구조체를 수정해야하는 경우에는 구조체의 인스턴스를 ref 매개 변수로 사용하는 정적 메서드를 정의하는 것이 좋습니다. 예 : SetPointXY(ref Point pt, int x, int y). 컴파일러는 구조체의 전달을 ref 매개 변수로 간주하여 해당 구조체를 수정하려고 시도하며 실제로 작동하는 상황에서만 허용합니다.

성능 측면에서 구조체 필드를 개별적으로 쓰는 것이 구조체를 업데이트하는 가장 빠른 방법이 아니라는 것은 구조체의 대부분이 기본값 또는 다른 미리 정의 된 구조체와 일치하는지 확인하는 것입니다. 기존 구조체. 기존의 인스턴스로 구조체를 덮어 쓰는 것이 더 빠를 수 있고 그런 다음 다른 것을 보유해야하는 필드를 작성하는 경우가있을 수 있지만 일반적으로 구조체를 업데이트하기 위해 메소드 나 함수를 사용해야한다고 제안합니다 코드는 필드를 개별적으로 설정하는 코드보다 읽기 쉽습니다.AreaCodePhoneNumber 유형의 공개 필드 인 경우 somePhoneNumber.AreaCode = "847";의 효과는 somePhoneNumber = new PhoneNumber("847", somePhoneNumber.Exchange, somePhoneNumber.Number, somePhoneNumber.Extension);의 효과보다 훨씬 명확합니다. 무엇보다도, 후자가 AreaCode 이외의 다른 필드를 변경하는지 여부를 알기 위해 전체 구조를 연구해야합니다. 반면에, 목표가 사실상 완전히 새로운 데이터를 제외하고는 공백 이었으면, 생성자 또는 팩토리 메서드를 사용하면 그렇게하고 있다는 사실을 명확히 알 수 있습니다. 단순히 구조체의 모든 필드를 개별적으로 덮어 쓰면 변경되지 않은 필드가 없음을 알기 위해 전체 구조체를 연구해야합니다.

관련 문제