2016-12-16 3 views
2

개체 클래스가 있고 각 개체의 속성 하나를 다른 모든 개체의 속성과 비교해야합니다. 일치하는 경우 코드는 무언가를해야합니다. 결과적으로 두 개의 'for 루프'가 객체를 통해 반복되어 해당 속성을 가져오고 두 번째 'for 루프'에서는 속성의 요소를 통과하는 세 번째 'for 루프'가 있습니다 (벡터). . 일치하는 경우, 현재 반복을 중단하고 다음 반복으로 넘어가려면 가장 바깥 쪽 'for 루프'가 필요합니다 (다른 객체와의 첫 번째 일치 만 고려해야 함).중첩 for 루프에서 continue 문과 같은 것을 사용하는 방법은 무엇입니까?

'goto'문을 살펴보고 do {} while() 구조를 만들었지 만 원하는 결과를 얻는 방법으로 구현하지 못했습니다. 내가 필요로하는 것은 가장 안쪽 루프의 조건문에서 일어나는 일을 기반으로 가장 바깥 쪽 루프에 대한 'continue'문과 같습니다.

이 작업을 수행하는 좋은 방법은 무엇이며 어떻게 구현해야합니까?

편집 : 내가 받아 들인 대답 옆에, 나는 또한 완벽하게 잘 작동하고 고토에 의존하지 않는 Martin Bonner의 대답을 추천 할 것이다. 'K'루프에서 조건문이 충족되는 경우

for (int i = 0; i < max; i++){ 
Object & object1 = system.getAgent(i); 
VectorOfStrings object_property1 = object1.getProperty(); 

    for (int j = i + 1; j < max; j++){ 
    Object & object2 = system.getObject(j); 
    VectorOfStrings object_property2 = object2.getProperty(); 

     for (unsigned int k = 0; k < object_property1.size(); k++){ 

      if (object_property1[k] == object_property2[k]){ 

      //do something 

      break; //this aborts the inner most loop 
      //Additionally, I need the outer most loop to move on one iteration 
      } 
     } 
    } 
} 

그래서, 나는 '내가'루프가 현재 반복을 중단하고 다음 단계로 이동하고 싶습니다.

또한 새롭기 때문에 코드가 멋지지 않을 수도 있지만이 특정 문제에 집중하십시오! 코드의 일반적인 구조 조정은 물론 :)의 문제에 대한 해결책이 될 수없는 한

+0

:

bool keep_going = true; for (int i = 0; i < max && keep_going; i++) { Object& object1 = system.getAgent(i); keep_going = !compare_objects(object1.getProperty(), i+1, max); } 

compare_objects이 같은 곳은 가장 바깥 쪽 루프가 하나의 반복에서 움직입니다 * 당신은 내가 증가하는 것을 의미합니까? object_property1과 object_property2의 크기가 같지 않으면 어떻게 될까요? – stijn

+0

덧붙여 말하자면 : "나는 영어로 어휘가 부족합니다."라고 말할 때까지, 나는 네가 나 같은 원어민 강사라고 생각했다. 영어는 괜찮습니다. –

+0

'do {...} while (false);'hack은 중첩 된 if-else의 중첩 루프를 피하는 데 효과적입니다. 'break'를 사용하여 스위치에서 빠져 나오기 때문입니다. – stefaanv

답변

7

goto로 구현 될 수있다 :

for (int i = 0; i < max; i++){ 
    Object & object1 = system.getAgent(i); 
    VectorOfStrings object_property1 = object1.getProperty(); 

    for (int j = i + 1; j < max; j++){ 
     Object & object2 = system.getObject(j); 
     VectorOfStrings object_property2 = object2.getProperty(); 
     for (unsigned int k = 0; k < object_property1.size(); k++){ 
      if (object_property1[k] == object_property2[k]){ 
       //do something 
       goto cnt; //this aborts the inner most loop 
       //Additionally, I need the outer most loop to move on one iteration 
      } 
     } 
    } 
    cnt:; 
} 

이것은 드문 경우 중 하나 goto의 사용이 정말 코드를 단순화입니다 .

+1

레이블을 'property_matched'와 같은 의미있는 이름으로 만들 것입니다. –

+0

정말 고마워요! 이것은 내가 필요로하는 것과 똑같이 작동합니다! – faranzki

+0

@MartinBonner 나는'cnt'가'continue'의 약자로 의미가 있음을 의미했습니다. – alexeykuzmin0

2

난 강력하게 alexeykuzmin0의 접근 방식 @ 추천,하지만 당신은 goto이 금지되는 환경에서 작업해야하는 경우, (성가신 플래그) 다음 대안은 다음과 같습니다

당신은 람다를 사용하고 반환 stament을 사용할 수 있습니다
for (int i = 0; i < max; i++){ 
    Object & object1 = system.getAgent(i); 
    VectorOfStrings object_property1 = object1.getProperty(); 

    bool property_matched = false; 
    for (int j = i + 1; j < max && !property_matched; j++){ 
     Object & object2 = system.getObject(j); 
     VectorOfStrings object_property2 = object2.getProperty(); 
     for (unsigned int k = 0; k < object_property1.size(); k++){ 
      if (object_property1[k] == object_property2[k]){ 
       //do something 
       property_matched = true; // This will break the "j" loop 
       break; //this aborts the inner most loop 
      } 
     } 
    } 
} 
+0

이 경우 성가신 것 같지 않습니다. 속성이 매치되었는지를 알고 싶을 것입니다. – stefaanv

+0

감사! 이 솔루션은 또한 완벽하게 잘 작동합니다! – faranzki

+0

@stefaanv : 예, 파이썬'for ... else ... '과 같은 것을 에뮬레이트하고 싶다면 플래그가 유용합니다. 반면에 레이블의 경우에는 중간에 바로 뒤에 "일치하지 않음"을 처리하는 코드 (계속할 수 있음)와 레이블 뒤에 "일치"를 처리하는 코드를 넣을 수 있습니다. –

2

컨트롤을 변경합니다. true를 반환하면 람다는 끝나고 "for"는 "계속"됩니다.

컴팩트 버전 :

for(;;) { 
    [&]() { 
     for(;;) { 
      if(/*break condition here*/) 
       return; 
     } 
    }(); 
} 

보다 일반적인 템플릿 :

for(;;) { 
    auto innerLoop = [&]() { 
     for(;;) { 
      if(/*break condition here*/) 
       return true; 
     } 
     return false; 
    }; 

    if(innerLoop()) 
     continue; 
} 

이 경우를 들어

for (int i = 0; i < max; i++){ 
    Object & object1 = system.getAgent(i); 
    VectorOfStrings object_property1 = object1.getProperty(); 

    auto innerLoop = [](){ 
     for (int j = i + 1; j < max; j++){ 
     Object & object2 = system.getObject(j); 
     VectorOfStrings object_property2 = object2.getProperty(); 

      for (unsigned int k = 0; k < object_property1.size(); k++){ 

       if (object_property1[k] == object_property2[k]){ 
        //do something 
        return true; 
       } 
      } 
     } 
     return false; 
    }; 

    if(innerLoop()) 
     continue; 
} 
+3

은 현명하지만, 그 당시에는 버섯이 많은 실독증 필자에 의해 조각 된 고대 서사적 태블릿만큼 읽기 쉽습니다. –

+0

내가 제공 한 코드를 기반으로 이것을 구현하는 방법에 대해 약간 혼란 스럽기 때문에 나는 이것을 테스트하지 않았다! if() 빈 뒤에 대괄호를 남겨 두어야합니까? – faranzki

+0

그것은 단지 템플리트 일뿐입니다. if()에 들어가기위한 조건입니다. – Bediver

3

이 고전적인 문제를 해결하는 가장 읽을 수있는 방법은 거의 항상 중첩 루프를 함수에 넣으십시오.나는 특정 코드가 수행하는 가정 무엇 모르겠지만, 여기에 솔루션을 기반으로 할 수있는 몇 가지 의사 코드입니다 : 내가 필요한 *

inline bool compare_objects (const VectorOfStrings& obj_prop1, size_t begin, size_t end) 
{ 
    for(size_t i=begin; i<end; i++) 
    { 
    Object& obj2 = system.getObject(j); 
    VectorOfStrings obj_prop2 = obj2.getProperty(); 

    for size_t j = 0; j < obj_prop1.size(); j++) 
    { 
     ifobj_prop1[j] == obj_prop2[j]) 
     { 
     do_something(); 
     return true; 
     } 
    } 
    } 

    return false; 
} 
관련 문제