1

내가하고있는 시스템은 다른 부울 속성으로 구성 될 수 있습니다. 서로 다른 구성의 이론적 인 최대 값은 2^n입니다. 여기서 n은 이러한 속성의 수입니다.패키지를 기반으로 구성 가능한 속성을 구성하고로드하는 방법은 무엇입니까?

프로덕션 코드와 분리 된 구성 도구가 있으며 부울 식을 사용하여로드되는 코드 패키지를 선택합니다. 이 도구는 isWithX 이상의 메소드 (예 : isWithXwithoutYwithZ)를 정의하는 클래스를 포함합니다. 패키지는 기본적으로 일부 메서드 정의를 정의하거나 재정의하는 클래스 확장 목록입니다. 패키지의 이름은 myPackageWithAWithoutBwithCwithDwithoutE입니다.

진화하는 부울 구성 속성이 있기 때문에 다른 패키지의 수와 이름의 크기가 어리 석다. 우리는 항상 스크롤하지 않고 이름을 볼 수 없습니다. 많은 코드 중복이 있습니다.

편집 :

  • 각 패키지에 대한 패키지 이름의 목록과 각 기능
  • 얼마나 많은 방법과 방법 : 생산 코드는 문제는 지금 그 문제에 국한되어있는 컨피그 속성에 액세스 할 수없는 이름 그들

지금 패키지 이름의 목록은 기본적으로 모든 다른이 같은 이름의 조합입니다 : 우리는 t을 필요로하는 구성없이 행동 별이있는 곳을 제외한 myPackageWithAWithoutBwithCwithDwithoutE o 구현.

지금은 각 패키지 및 각 기능에 대해 : 기능 당 패키지 이름 당 1 개의 메소드.

+1

패키지 이름을 변경할 수 있습니까? 즉, 모든 패키지에 포함 ('myPackageWithX')을 정의한 다음 n 개의 패키지를 혼합하여 구성에 맞게 혼합 할 수 있습니까? –

+0

에서 myPackageWithXwithoutY 및 myPackageWithXwithY myPackageWithX라는 '부모'패키지를 만들고 일부 복제본을 제거 할 수 있지만 if 문이나 부모문에서 if 문을 사용하지 않으면 모든 하위 패키지 내용을 제거 할 수 없습니다. – Rivenfall

답변

3

특정 문제를 해결하는 방법을 알려줄 수는 없으므로 실제로 사용할 디자인을 찾는 데 도움이되는 몇 가지 힌트를 알려 드리겠습니다. ConfigurationSettings는 특정 섹션에 속하는/쓰기 설정을 읽을 기본적인 서비스를 제공

ConfigurationSettings 
    ApplicationSettings 
    UserSettings 
    DisplaySettings 
    ... 

추상 클래스 :

는 구성 개체의 계층 구조를 생각해 보자. 계층 구조를 사용하면 선택기를 다른 하위 클래스에서 다시 구현할 수 있으므로 명명 규칙이 단순 해집니다.

ApplicationSettings 서브 클래스는 다른 역할을한다 : 그것의 registry 인스턴스 변수에 모든 섹션을 등록하는 키가 섹션 이름과 값을 해당 서브 클래스의 인스턴스 Dictionary :

ApplicationSettings current register: anEmailSettings under: `Email` 

추상 클래스가 제공하는이 읽기 및 쓰기 설정을위한 기본 서비스 :

하위 클래스는이 서비스를 사용하여 개별 설정에 액세스하고 클라이언트가 현재 구성 is, has, supports 등의 특정 기능 또는 조합 여부를 테스트합니다. 이러한보다 구체적인 방법은보다 기본적인 (settingAt:for:) 측면에서 구현됩니다.새 패키지는 자신의 서브 클래스를 등록 할 때 다음과 같이

는 시험 방법을 사용할 수있게 :

self <section>Settings isThisButNotThat 

경우, 예를 들어,

emailSettings 
    ^(ApplicationSettings current for: 'Email') isThisButNotThat 

유사하게 다른 섹션

. 위에서 언급했듯이 하위 클래스의 구분을 사용하면 암시 적으로 #isEmailThisButNotThat 대신 #isThisButNotThat 섹션을 참조하는 간단한 선택기를 사용할 수 있습니다.

두 가지 방법에 의해 제공되는 설정을 수정할 수있는 사용자에 대한 대화 상자를 적용/취소 지원하는 것이 중요하다 또 다른 기능 : 당신이 GUI를 열 때,

ConfigurationSettings >> #readFrom: 

하고 그래서

ConfigurationSettings >> #writeOn: 

현재 인스턴스에서 사본을 열지 않은 설정을 표시합니다.

settings := ApplicationSettings new readFrom: ApplicationSettings current. 

그런 다음 GUI에이 복사본을 사용자에게 제시합니다. 사용자가 대화 상자를 취소하면 사본을 잊어 버리게됩니다.

ApplicationSettings >> readFrom: anApplicationSettings 
    registry keysAndValuesDo: [:area :settings | | section | 
    section := anApplicationSettings for: area. 
    settings readFrom: section] 

이 가 가
ApplicationSettings >> writeOn: anApplicationSettings 
    registry keysAndValuesDo: [:area :settings | | settings | 
    section := anApplicationSettings for: area. 
    settings writeOn: section] 
0

나는 완전히 모든 이해가 안 :

settings writeOn: ApplicationSettings current 

이 두 서비스의 구현은 간단한 패턴을 다음과 : 그렇지 않으면 당신은 변경이 방법을 적용 문제의 측면을 다루지 만 역동적 인 접근 방식을 사용할 수도 있습니다. 예를 들어, 패키지 이름을 구성에 보낸 선택기를 분석하고 추출하는 #doesNotUnderstand:을 무시할 수 :

다음
doesNotUnderstand: aMessage 
| stream included excluded | 
"parse selectors like #isWithXwithoutYwithoutZ" 
stream := (#isWithXwithoutYwithoutZ allButFirst: 6) asLowercase readStream. 
included := Set new. 
excluded := Set new. 
[ stream atEnd ] whileFalse: [ 
    (stream peek: 3) = 'out' 
     ifTrue: [ 
      stream next: 3. 
      excluded add: (stream upToAll: 'with') ] 
     ifFalse: [ included add: (stream upToAll: 'with') ] ]. 

, 당신이 필요로하는 모든 그에서 패키지 목록을 (I 희망)를 생성 할 수있는 좀 더 코드 .

+0

이러한 패키지 이름은 처음에는 존재하지 않아야합니다. 프레임 워크의 다른 디자인을 찾고 있습니다. 퍼포먼스와 팀웍에 신경 쓰지 않는다면, doesNotUnderstand, 정규 표현식, 동적으로 컴파일 된 메소드 등을 사용하여 그런 종류의 작품을 해킹 할 수 있습니다. 그렇지만 if 문을 사용하는 것은 허용되지 않습니다. – Rivenfall

+1

입니다. 질문에 세부 사항을 추가 할 수 있습니까? 예를 들면 : 법적 수정은 무엇이며 어디서 만들 수 있습니까? 목표 (예 : 패키지 이름 제거)는 무엇입니까? –

+0

if 문을 사용할 수없는 이유를 이해 한 지금 질문을 단순화했습니다. – Rivenfall