ORDERING 문제 질문입니다

  • mju6229
    mju6229
    #define _CRT_SECURE_NO_WARNINGS
    # include <iostream>
    # include <cstring>
    
    char arr[101][2];
    int num[200];
    int check[200];
    
    int main(){
        int t,i,j,k;
        int a,b,cnt;
    
        scanf("%d",&t);
    
        for(i=0;i<t;i++){
            scanf("%d %d",&a,&b);
            cnt=a;
    
            for(j=0;j<b;j++){
                scanf("\n%c%c",&arr[j][0],&arr[j][1]);
                num[arr[j][1]]++;
            }
            while(cnt>0){
                for(j=0;j<a;j++){
                    if(num[65+j] <= 0){
                        if(num[65+j]<=0 && check[65+j] !=1){
                            printf("%c",65+j);
                            check[65+j] = 1;
                            cnt--;
                        }
                        for(k=0;k<b;k++){
                            if(arr[k][0] == j+65){
                                num[arr[k][1]]--;
                            }
                        }
                        for(k=0;k<j;k++){
                            if(num[65+k]<=0 && check[65+k] !=1){
                                printf("%c",65+k);
                                check[65+k] = 1;
                                cnt--;
                            }
                        }
                    }
                }
            }
            printf("\n");
    
            memset(num,0,sizeof(num));
            memset(check,0,sizeof(check));
        }
        return 0;
    }
    

    어떤 테스트케이스에서 오답이 나는지 못찾겠어서 도움을 요청합니다
    코드는 예를 들어 설명하겠습니다.

    ex)
    1
    4 4 - a와 b
    DA
    BD
    CA
    CD

    일 때 A와 D는 출력하기 위해서 앞에 2가지씩 먼저 출력해야 하는 알파벳들을 가지고 있습니다. 이 경우 아스키코드 숫자를 이용해 num[65] = 2가 되고 num[68] = 2 가 됩니다. 그 후 while문으로 들어가게 됩니다. while문의 조건인 cnt는 a의 숫자인 4로 초기화 시켜준 후 A B C D 알파벳이 하나씩 출력되었을 때 -1씩 감소시켜 0이하가 되었을 때 반복문에서 빠져나올 수 있게 했습니다. 이제 아스키코드를 이용하여 A부터 차례대로 D까지 봅니다. num = 0 (즉, 앞에 먼저 출력되어야 하는 알파벳이 없거나 이미 다 출력되었을 경우) check != 1 (아직 한번도 출력되지 않은 경우) 이 두가지 조건을 만족 하는 알파벳을 출력시킵니다. 출력시키고 난 후 이 알파벳을 출력했다고 기록하기 위해 check = 1로 변경시켜주고 이제 4개의 알파벳 중 3개의 알파벳만 더 출력하면 되기 때문에 cnt를 1씩 감소시켜줍니다. 위의 예제에서 이를 가장 먼저 만족시켜 주는 알파벳이 B이기에 B를 먼저 출력을 해줍니다. 출력 후 B가 먼저 나와야 자기자신이 출력될 수 있는 알파벳을 조건에서 전부 훑어줍니다. 두 번째 조건인 BD가 이에 해당됨으로 D는 B가출력됨으로써 num[68]은 -1감소되어 num[68] = 1이 됩니다. 그 후 혹시 B이전 알파벳 중 혹시 B가 출력됨으로써 num이 0이 된 알파벳이 있나 찾아보고 있으면 이를 출력시킵니다. B이전 알파벳은 A밖에 없는데 A가출력되기위해서 먼저 출력되어야 하는 알파벳은 D와 C로 이에 해당되지 않기때문에 무시하고 넘어가게 됩니다. B는 이제 출력되었고 이제 C를 봅니다 C역시 num = 0 , check = 0이기에 출력이되고 C가 출력됨으로써 A와 D의 num은 -1씩 감소하여 num[65] = 1 , num[68] = 0이 됩니다. 그리고 C이전인 알파벳 A와 B중 혹시 num이 0 이되었고 check !=1인 것이 있는지 찾아봅니다. 역시이에 해당되는 알파벳이 없기때문에 무시하고 넘어가게됩니다. 이제 D를 보게 되는데 D의 선행알파벳들이 모두 출력되어 D도 num=0 , check != 1이기에 출력됩니다. 그리고 D가 출력됨으로써 A의 num = 0이됩니다. 그 후 D의 전 알파벳인 A B C를 한번씩 보면서 num = 0이고 check != 1인 알파벳을 찾아보는데 A가 이에 해당하기 때문에 A도 출력을 합니다. 모든 알파벳이 출력되었기 때문에 while 반복문도 종료하게 됩니다.

    ㅠㅠ 이렇게 돌아가는데 어떤 케이스에서 잘못되어 오답이 나오는지 모르겠습니다.


    7년 전
2개의 댓글이 있습니다.
  • JongMan
    JongMan
    for(k=0;k<j;k++){
                            if(num[65+k]<=0 && check[65+k] !=1){
                                printf("%c",65+k);
                                check[65+k] = 1;
                                cnt--;
                            }
                        }

    부분에 문제가 있는 것 같네요.

    1
    5 4
    AE
    EB
    ED
    BC

    해당 루프를 아예 없애시는 게 좋을 것 같네요.


    7년 전 link
  • mju6229
    mju6229

    아 생각하지도 못한 부분에서 오류가 있었네요 !! 감사합니다 덕분에 통과했어요 정말 감사합니다!!


    7년 전 link
  • 정회원 권한이 있어야 커멘트를 다실 수 있습니다. 정회원이 되시려면 온라인 저지에서 5문제 이상을 푸시고, 가입 후 7일 이상이 지나셔야 합니다. 현재 문제를 푸셨습니다.