KeyValuePair와 같은 사전 구축 된 구조에 대해 2 속성 클래스를 언제 사용해야합니까?


31

키 / 값 유형의 데이터를 사전 빌드 된 일반 구조 (예 : KeyValuePair 또는 Tuple? 합니까?

예를 들어 내가 만든 대부분의 ComboBox에는 DisplayName과 Value가 있습니다. 이것은 새로운 클래스에 넣을 때와 KeyValuePair를 사용할 때를 결정하려고하는 일종의 데이터입니다.

나는 현재을 사용하는 무언가를 연구 iCalendar하고 있으며 선택한 사용자의 데이터는 궁극적으로 key1=value1;key2=value2;문자열 유형으로 결합됩니다 . 데이터를에 넣는 것으로 시작 KeyValuePair<string,string>했지만 이제는 그것이 자체 클래스인지 궁금합니다.

전반적으로, 저는 KeyValuePair2- 속성 객체 와 같은 기존 구조 / 클래스를 사용하기로 결정할 때 어떤 가이드 라인이 사용되는지 , 그리고 어떤 상황에서 당신이 서로를 사용할 것인지에 관심이 있습니다.


3
어떤 언어? 파이썬에서는 tuple타입이 있기 때문에이 딜레마가 없습니다 .
S.Lott

3
@ S.Lott-.NET BCL에는 v 4.0 이후 튜플이 있습니다.
Oded

1
.NET 4에는 튜플 유형도 있습니다. msdn.microsoft.com/ko-kr/library/system.tuple.aspx
Dave Nay

1
이 경우 @Oded, 내가 뭔가를 구축하고 iCalendar난에 대한 객체를 원 BYDAY하고 BYSETPOS. 그것들은 콤보 key=value;
Rachel

4
@Rachel : 보다 구체적으로 질문을 업데이트 하십시오. 많은 의견이 사물을 명확히하는 가장 좋은 방법은 아닙니다.
S.Lott

답변:


26

나는 대부분의 경우 일반적으로 KeyValuePair 또는 Tuple 대신 객체를 사용합니다. 먼저, 6 개월 후에 변경을하려고 할 때, 무엇을 궁금해하기보다는 의도가 더 이른 지 알아내는 것이 훨씬 쉽습니다.Tuple t 하고 왜 그 재미있는 가치가 . 둘째, 상황이 커지고 변화함에 따라 필요한만큼 간단한 데이터 전송 객체 동작을 쉽게 제공 할 수 있습니다. 두 가지 이름 형식이 필요하십니까? 적절한 ToString () 오버로드를 추가하기 만하면됩니다. 인터페이스를 구현해야합니까? 문제 없어. 마지막으로, 자동 속성 및 코드 완성과 같은 간단한 개체를 만드는 데 거의 오버 헤드가 거의 없습니다.

보너스 팁 : 이러한 객체가 네임 스페이스를 오염시키지 않도록하려면 클래스 내부에 개인 클래스를 만드는 것이 물건을 감싸고 이상한 종속성을 방지하는 좋은 방법입니다.


1
DTO = 데이터 전송 객체 ? -나는 TLA가 싫어 ;-)
Ben

3
@Ben-TFTFY. . .
Wyatt Barnett 2016 년

7

새 클래스를 정의하는 규칙은 간단합니다. "Occam 's Razor"로 요약됩니다.

http://c2.com/cgi/wiki?OccamsRazor

정당한 이유없이 새로운 수업을 도입하지 마십시오. 또는 미리 작성된 클래스를 최대한 사용하십시오. 또는 가능한 적게 발명하십시오. 그러나 적은 코드를 작성하는 것이 편합니다.

객체에 고유 한 책임을 할당해야하고 사전 작성된 클래스에 해당 책임이 정의되어 있지 않으면 사전 작성된 클래스를 사용할 수 없습니다. 종종 이것은 독특한 방법입니다.

tuple이상이 KeyValuePair바람직하다.

까지.

A tuple또는의 일부가 아닌 일부 기능이 필요합니다 KeyValuePair. 그런 다음 자신의 클래스를 정의해야합니다.



1
시맨틱 이 " tuple또는 KeyValuePair"의 일부가 아닌 기능 "으로 간주 됩니까? KeyValuePair는 최소한 일부 형태의 의미론을 가지고 있지만 튜플은 거의 (상황에 따라 가능할 수 있음) imho를 수행하지 않습니다. 새로운 클래스를 도입하면 당연히 명확한 의미를 제공 할 수 있습니다.
Mal Ross

+1 플러그에 맞는 덕트 테이프로 보트 전체를 패치하지 마십시오.
Evan Plaice

4
나는 이것이 Occam의 면도기를 잘못 사용했다고 생각합니다. 둘째, 변수에 어떤 정보가 포함되어 있는지 아는 것이 중요합니다. -1.
Bent

4

자신의 수업을 작성하는 경우 두 값이 무엇인지에 대한 문서를 보관할 수있는 명확한 장소가 있습니다. 특히 두 문자열은 매우 명확한 정의가 아니기 때문에. 그러나 당신은 같은 것을 쓸 수 있습니다

 public class MyPair : Tuple<string, string>

나는 MyPairTuple 값이 무엇이고 무엇을 사용하는지 정의 하기 때문에 이것을 좋아합니다 .
IAbstract

2
그러나 다음 속성을 호출 할 것 Item1Item2! 전체 클래스를 정의하는 것이 쉽지 않습니까? public class SideStrings { public string Left { get; set; } public string Right { get; set; } }
구성자

@configurator 나는 그것에 대한 응답을 작성하고 Tuple이 읽기 전용이라는 것을 알았으므로 나는 모든 것을 바보라고 생각합니다. 튜플을 감싸서 원하는 값을 지정할 수 있습니다.
Sign

2
@Sign :하지만 요점이 뭐야? 자신 만의 클래스를 만드는 것은 튜플을 감싸는 보다 덜 효과적 입니다.
구성자

2
@configurator는 커스텀 객체보다 더 나은 평등 및 비교 항목을 얻지 만 설정이 필요한 경우 튜플은 확실히 잘못된 방법입니다.
서명

4

S. 로트가 쓴

정당한 이유없이 새로운 수업을 도입하지 마십시오. 또는 미리 작성된 클래스를 최대한 사용하십시오. 가능한 한 적게 발명하십시오.

사전 빌드 클래스에 정의되지 않은 오브젝트에 고유 한 책임을 지정해야하는 경우 사전 빌드 클래스를 사용할 수 없습니다.

왜 이것에 심각한 문제가 있는지 말씀 드리겠습니다. 이후

KeyValuePair [문자열, 문자열]

괜찮은 것 같습니다 .... KeyValue [문자열, KeyValue [문자열, KeyValuePair [문자열, 문자열]]]도 괜찮습니까? 나는 S.Lott가 이것에 대해 무엇을 말할지 모르지만, 상사 그것이 괜찮다고 생각합니다 .

나는 동의하지 않는다. 그리고 그 이유 는 다음과 같습니다. 다음 코드의 가독성 이 떨어 집니다. 이러한 데이터 구조를 채울 기능은 훨씬 더 복잡하고 오류가있을 것이다 (ERR .. 예외) 경향 (상상할 적어도 일부 비즈니스 로직뿐만 아니라). 나는 상사와 너무 많이 논쟁하지 않았지만 여기서 말할 것입니다 : 가독성은 공간 절약을 능가합니다 ( 그의 논쟁 ). 따라서 일부 필드가있는 클래스 객체는 아닙니다. 그러나 일부는 때때로 빈 상태로 유지하는 것이 더 나을까요?

추신 : 나는 Ultra_Noob이므로 내가 틀렸다면 알려주십시오.


2
나는이 생각하는 KeyValuePair<string,string>것들이 넣어 실제로 키와 값입니다 가정, 괜찮습니다. 코드 작성을 저장하고 상호 운용성을 확보하기 때문에 기존 클래스를 재사용하는 것이 좋습니다 . OTOH, KeyValuePair<string,KeyValuePair<string,string>>대부분의 경우 와 같이 복잡한 것을 사용 하면 실제로는 너무 복잡합니다. 추가 기능이 필요하지 않은 경우, 의미가 분명하거나 다른 클래스와 잘 작동하는 경우가 있습니다. YMMV, 이것은 단지 장점과 대조를 가중시킵니다.
maaartinus

C #을 사용 하는 경우 Tuple vs KeyValuePair성능 은 다음과 같습니다 . 상사와 공유하고 싶은 것이 있습니까?
Ben

3

키 / 값 쌍 을 말할 때 일반적으로 해시 테이블 또는 연관 배열 또는 간단히 KeyValuePair 객체를 생각합니다. 나는 그것들을 모두 사용하며 어느 것을 사용할 때 차이가 없습니다.

키 / 값 쌍 목록에서 가장 중요한 것은 가 고유해야하며 (결국 키이므로) 위에서 언급 한 모든 구조가 실제로 그 기능을 제공한다는 것입니다.

그 외에도 키로 검색하거나 푸시 및 팝과 같은 목록 (배열) 스타일 작업을 수행하고 싶습니다.

그래서 제 대답은 NO입니다 . 많은 내장 구조가 이미 저를 위해 그렇게하기 때문에 키 / 값 쌍에 대해 명시 적으로 객체를 만들지 않습니다.


3

Clean Code의 6 장 에는 데이터 구조와 클래스를 사용할시기에 대한 자세한 설명이 있습니다. 간단히 말해서, 해당 데이터에서 작동 할 새 기능을 추가 할 것으로 예상되는 경우 데이터 구조를 사용합니다. 기존 함수에서 작동 할 새 데이터 유형을 추가 할 것으로 예상되는 경우 클래스를 사용합니다. ComboBox는 후자의 예입니다. 많은 다른 데이터 유형 (다른 위젯에 대해 다른 종류의 데이터)에서 작동하는 하나의 함수 세트 (ComboBox 구현)가 있습니다.


2

나는 아마도 Wilding에 동의 할 것이다 . 그러나 나는 이런 종류의 일에도 약간의 멍청한 놈이다.

내장 유형은 종종 메커니즘 객체 라고 제안 합니다. 예를 들어 KeyValuePair는 사전 및 해시 테이블 메커니즘의 일부로 고유 키를 보장하고 메커니즘 자체의 컨텍스트 내에서 의미있는 이름을 갖는 속성을 갖도록 도와줍니다.

반면, 맞춤형 데이터 개체를 사용하면 데이터를보다 잘 표현할 수 있으며 가독성 및 확장 성을 비롯한 많은 이점을 얻을 수 있습니다. Sign이 제안한 것처럼 사용자 정의 빌드 객체에서 기존 코드의 재사용을 중지하는 것은 없지만 랩핑 된 클래스를 숨기고 추상화 누출을 피하여 나중에 나머지 코드에 영향을 미치지 않고 기본 구현을 변경할 수 있습니다. .

실제 질문 : 당신은 데이터를 표현하고 있습니까 아니면 데이터를 메커니즘에 사용하고 있습니까? (그리고 나는 이러한 개념들을 혼합하여 사용하지 않는 것이 좋습니다).

내 경험상 Tuple [string, string]이 메소드에 전달되고 Item1과 Item2가 무엇인지 즉시 알 수있는 방법이 없다는 것을 나쁘게 생각합니다. 메서드 내에서 또는 클래스의 개인 멤버로만 튜플을 사용하는 것이 가장 좋습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.