[C++로 풀이] 브라이언의 고민⭐⭐⭐

Date:     Updated:

카테고리:

태그:

📌 브라이언의 고민

난이도 ⭐⭐⭐

🚀 문제

image

image

Level 3 문제들 중에서 풀은 사람 수가 가장 적은 문제이길래 겁이 나서.. 제일 뒤로 미뤘었던 문제인데ㅋㅋㅋ 드디어 풀어 보게 되었다! 역시 풀은 사람의 수가 적은건 이유가 있다.. 구현이 넘 까다로웠다.. 하..ㅠㅠㅋㅋㅋㅋㅋㅋ 연습장에 구현해야할 조건들을 수기로 쭉 정리해본 후 코드를 짰다. 연습장 두 페이지를 꽉꽉 채웠다


🚀 내 풀이 ⭕

#include <string>
#include <vector>

using namespace std;

string solution(string sentence) {
    string answer = "";
    const string invalid = "invalid";
    vector<string> words;
    vector<bool> checked(26);
    bool first_rule = false;
    bool second_rule = false;
    char char_rule1 = NULL;
    char char_rule2 = NULL;
    string word = "";

    for (int i = 0; i < sentence.length(); ++i) {
        if (first_rule && second_rule) {
            if (isupper(sentence[i])) {
                word += sentence[i];

                if (i + 1 == sentence.length())
                    return invalid;
                else if (isupper(sentence[i + 1]))
                    return invalid;
                else if (char_rule1 != sentence[i + 1] && char_rule2 != sentence[i + 1])
                    return invalid;
            }
            if (islower(sentence[i])) {
                if (char_rule2 == sentence[i]) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;

                    second_rule = false;
                    checked[char_rule2 - 'a'] = true;
                    char_rule2 = NULL;

                    words.push_back(word);
                    word = "";

                    continue;
                }
                if (i + 1 == sentence.length())
                    return "invalid";
                else if (islower(sentence[i + 1]))
                    return "invalid";
            }
        }
        else if (first_rule) {
            if (isupper(sentence[i])) {
                word += sentence[i];

                if (i + 1 == sentence.length()) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;
                    words.push_back(word);
                    word = "";
                }
                else if (isupper(sentence[i + 1])) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;
                    words.push_back(word);
                    word = "";
                }
                else if (char_rule1 != sentence[i + 1]) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;
                    words.push_back(word);
                    word = "";
                }
            }
            if (islower(sentence[i])) {
                if (i + 1 == sentence.length())
                    return invalid;
                else if (islower(sentence[i + 1]))
                    return invalid;
            }
        }
        else if (second_rule) {
            if (isupper(sentence[i])) {
                word += sentence[i];

                if (i + 1 == sentence.length())
                    return invalid;
                else if (islower(sentence[i + 1]) && char_rule2 != sentence[i + 1]) {
                    if (char_rule2 == sentence[i - 1]) {
                        if (checked[sentence[i + 1] - 'a'])
                            return invalid;
                        first_rule = true;
                        char_rule1 = sentence[i + 1];
                    }
                    else
                        return invalid;
                }
            }
            if (islower(sentence[i])) {
                second_rule = false;
                checked[char_rule2 - 'a'] = true;
                char_rule2 = NULL;
                words.push_back(word);
                word = "";
            }
        }
        else {
            if (isupper(sentence[i])) {
                word += sentence[i];
                first_rule = true;
       
                if (i + 1 == sentence.length()) {
                    first_rule = false;
                    words.push_back(word);
                    word = "";
                }
                else if (isupper(sentence[i + 1])) {
                    first_rule = false;
                    words.push_back(word);
                    word = "";
                }
                else if (islower(sentence[i + 1])) {
                    if (checked[sentence[i + 1] - 'a'])
                        return invalid;
                    char_rule1 = sentence[i + 1];
                    vector<int> pos;
                    for (int j = i + 1; j < sentence.length(); ++j) 
                        if (sentence[j] == char_rule1)
                            pos.push_back(j);
                    if (pos.size() == 1)
                        continue;
                    else if (pos.size() >= 3) {
                        bool flag = true;
                        for (int j = 1; j < pos.size(); ++j) {
                            if (pos[i + 1] - pos[i] != 2) {
                                flag = false;
                                break;
                            }
                        }
                        if (flag)
                            continue;
                    }
                    else {
                        first_rule = false;
                        char_rule1 = NULL;
                        words.push_back(word);
                        word = "";
                    }
                }
            }
            if (islower(sentence[i])) {
                if (checked[sentence[i] - 'a'])
                    return invalid;
                if (i + 1 == sentence.length())
                    return invalid;
                else if (islower(sentence[i + 1]))
                    return invalid;
                second_rule = true;
                char_rule2 = sentence[i];
            }
        }
    }

    for (int i = 0; i < words.size(); ++i)
        answer += (words[i] + " ");
    answer.pop_back();
    return answer;
}

image

10 점 ~.~ 브라이언의 고민 문제를 마지막으로, 현재 기준 프로그래머스에 있는 모든 Level 1, 2, 3 문제를 전부 다 풀었다. 짝짝짝 👏👏👏

🔥 해설

    string answer = "";
    const string invalid = "invalid"; // 직접 return "invalid"; 하드코딩하고 다니면 오타 생길까봐 따로 변수로 선언하여 여기에 "invalid" 문자열을 저장하였다.
    vector<string> words; // 하나의 규칙 상태가 끝날 때마다 완성된 단어를 이 곳에 저장. 추후 이 곳에서 하나 하나씩 빼서 answer 에 덧붙일 것이다.
    vector<bool> checked(26); // 알파벳(인덱스)별로 특수문자로 쓰인 소문자 체크
    bool first_rule = false; // 현재 규칙 1 상태라면 true 
    bool second_rule = false; // 현재 규칙 2 상태라면 true
    char char_rule1 = NULL; // 현재 규칙 1 상태일 때 특수문자로 쓰이는 소문자 저장
    char char_rule2 = NULL; // 현재 규칙 2 상태일 때 특수문자로 쓰이는 소문자 저장
    string word = ""; // 아직 완성되지 않은 단어! 현재 규칙 상태에서 만들어나가는 중

나는 노가다로..😂 현재 규칙 1 상태인지, 규칙 2 상태인지를 구분하고 그 안에서 현재 문자가 대문자일 때, 소문자 일 때 등등 이렇게 세세하게 분기 하여 조건을 정리하였다.

  • 밑줄 친 부분이 해당 규칙을 가진 하나의 독립적인 단어이다.
    • 규칙 1
      • ex) ObWorldb, OaObOb, OaOaOaOO
    • 규칙 2
      • ex) aOa, OaOa, OaOOa, aOOOOOabOb
    • 규칙 1 + 2
      • ex) aObOa, aObObOa, OaObOa

OaOaO는 규칙 1 이라고 해석될 수도 있지만 O(규칙 1) + aOa(규칙 2) + O(규칙 1) 이렇게 쪼개서 생각할 수도 있다. 최대한 짧은 단어로 쪼개서 생각하는게 반례가 덜 생길 것 같아서 OaOaOOOO 단어가 아닌, O + aOa + O 로써, 즉 O O O 이렇게 3 개의 단어로 해석되도록 코드를 짰다. 따라서 내 코드를 실행하면 “SpIpGpOpNpGJqOqA” 는 “SIGONG JOA”가 아닌, “SIGONG J O A” 결과를 리턴한다.


1️⃣ 규칙 1 상태도 아니고, 규칙 2 상태도 아닐 때 : else


이 부분의 전체 코드 펼쳐서 확인하기 Click ✨
        else { // 규칙 1 상태도 아니고, 규칙 2 상태도 아닐 때. 즉 아무 상태도 아닐 때
            if (isupper(sentence[i])) {
                word += sentence[i];
                first_rule = true;
       
                if (i + 1 == sentence.length()) {
                    first_rule = false;
                    words.push_back(word);
                    word = "";
                }
                else if (isupper(sentence[i + 1])) {
                    first_rule = false;
                    words.push_back(word);
                    word = "";
                }
                else if (islower(sentence[i + 1])) {
                    if (checked[sentence[i + 1] - 'a'])
                        return invalid;
                    char_rule1 = sentence[i + 1];
                    vector<int> pos;
                    for (int j = i + 1; j < sentence.length(); ++j) 
                        if (sentence[j] == char_rule1)
                            pos.push_back(j);
                    if (pos.size() == 1)
                        continue;
                    else if (pos.size() >= 3) {
                        bool flag = true;
                        for (int j = 1; j < pos.size(); ++j) {
                            if (pos[i + 1] - pos[i] != 2) {
                                flag = false;
                                break;
                            }
                        }
                        if (flag)
                            continue;
                    }
                    else {
                        first_rule = false;
                        char_rule1 = NULL;
                        words.push_back(word);
                        word = "";
                    }
                }
            }
            if (islower(sentence[i])) {
                if (checked[sentence[i] - 'a'])
                    return invalid;
                if (i + 1 == sentence.length())
                    return invalid;
                else if (islower(sentence[i + 1]))
                    return invalid;
                second_rule = true;
                char_rule2 = sentence[i];
            }
        }

즉, 현재 아무런 규칙이 없을 때다. 새로운 단어가 시작할 때인 것이다!

현재 문자가 대문자일 때 : if (isupper(sentence[i]))

현재 아무런 규칙 상태가 아닌데 현재 문자가 대문자라면 규칙 1 에 해당하는 단어가 시작된다는 것이다.

  • 현재 문자는 규칙 1 단어의 첫 문자가 된다.
    word += sentence[i];
    first_rule = true; // 규칙 1 ON
    
  • 다음 문자가 범위를 넘어설 때 ex) O
    • 즉, sentence의 마지막 문자일 때다. 이땐 무조건 O 한 문자짜리 단어로 끝나야 한다.
    • 한 단어가 바로 끝났으니 위에서 규칙 1 ON 했던걸 다시 OFF 해준다.
      if (i + 1 == sentence.length()) {
          first_rule = false; // 규칙 1 OFF
          words.push_back(word); // 단어 추가
          word = ""; // 리셋
      }
      
  • 다음 문자가 대문자일 때 ex) OA
    • 현재 규칙 1 이므로 다음 문자가 대문자라는 것은 현재 문자까지가 하나의 단어 끝이라는 것이다. 따라서 O 한 문자짜리 단어로 끝나야 한다.
    • 한 단어가 바로 끝났으니 위에서 규칙 1 ON 했던걸 다시 OFF 해준다.
      else if (isupper(sentence[i + 1])) {
          first_rule = false;  // 규칙 1 OFF
          words.push_back(word); // 단어 추가
          word = ""; // 리셋
      }
      
  • 다음 문자가 소문자일 때 ⭐
    • 다음 문자인 소문자가 규칙 1 의 특수문자도 될 수 있고. 규칙 2 의 특수문자도 될 수 있고, 규칙 1 + 2 의 특수문자도 될 수 있기 때문에 규칙 1 의 특수문자인지, 규칙 2 의 특수문자인지, 규칙 1+2 의 특수문자인지를 검사해야 한다.
      • 단어의 첫 소문자이니 사용 여부 체크
        • 다른 단어에 사용된적이 있다면 “invalid”
      • 규칙 1 의 소문자라면
        • 대문자인 현재 문자는 대문자 한 문자로 단어가 끝나지 않는다. 규칙 1 의 특수문자(소문자)가 있으니 하나의 단어를 이루는 문자가 뒤에 더 있다는 뜻이다.
        • 조건
          • 👉 다음 문자와 동일한 소문자가 1 개만 있어야 한다. ex) OaO
          • 👉 다음 문자와 동일한 소문자가 대문자 사이 사이에 3 개씩 이상 있어야 한다. ex) OaOaOaO
      • 규칙 2 혹은 규칙 1 + 2 의 소문자라면
        • 한 문자짜리 단어로 끝나야 한다. 그 뒤는 규칙 2 의 소문자기 떄문에 대문자인 현재 문자와는 관련 없는 것으로 취급해야 한다. 규칙 1 인 현재 문자 하나로 단어 끝내야 함.
        • 👉 규칙 1 의 소문자의 규칙을 제외한 모든 현상!! 다음 문자와 동일한 소문자가 2 개 있다던가 소문자가 대문자 사이 사이에는 있지는 않은 등등.. *ex) OaOa, OaOOOa, OaObObOa(다음 문자와 일치하는 a가 2개인것만 본다.)
        • 위에서 설명했지만 OaOaO 이렇게 소문자가 2 개 있는 것은 O, aOa, O 로 볼 것이다.
        • OaOOOOOaOOa 이건 사실 invalid 한 문장이다. aOOOOOa로, 규칙 2 에 의하여 a 가 모두 쓰였지만 세 번쨰 a 가 또나오기 때문이다. 세번째 a가 invalid 하다는건 나중 가서 검사하게 될 것이니 이 단계에선 신경쓰지 않아도 된다. 일단 사이사이에 있진 않았으니 규칙 1 의 소문자는 아니라고 판단 정도만 하면 된다.
          // 다음 문자가 소문자라면
          else if (islower(sentence[i + 1])) { 
          // 단어의 첫 소문자이니 방문 체크 (이미 이전 단어에서 쓰인적이 있는 특수문자인지) 
          if (checked[sentence[i + 1] - 'a']) 
              return invalid; // 있다면 invalid 리턴 후 종료
                  
          char_rule1 = sentence[i + 1]; // 현재 문자는 규칙 1 단어의 첫 문자. 소문자인 다음 문자가 규칙 1 의 특수문자가 될 수 있으므로 미리 저장해둠
          vector<int> pos; // 소문자인 다음 문자와 동일한 소문자들의 위치를 모두 pos 에 저장. pos.size()가 곧 해당 소문자의 개수가 된다.
          // 다음 문자부터 범위 끝까지 다음 문자(특수문자)와 동일한 문자의 인덱스를 pos 에 삽입한다.
          for (int j = i + 1; j < sentence.length(); ++j) 
              if (sentence[j] == char_rule1)
                  pos.push_back(j);
          // 1. 하나 밖에 없다는건 다음 문자인 소문자가 규칙 1 단어의 특수문자가 되야한다는 것. ex) OaO 
          // char_rule1 도 위에서 등록해놨으니 딱히 할게 없어서 continue (그래도 if문 따로 쓴 이유는 e규칙 2 단어의 특수문자가 되도록 하는 경우들을 전부 'else' 하나로 처리하기 위하여)
          if (pos.size() == 1)
              continue;
          // 2. 3개 이상인데 모두 대문자 사이사이에 인덱스 2 차이로 있을 때에도 다음 문자인 소문자가가 규칙 1 단어의 특수문자가 되야한다는 것. ex) AaBaCaDaE
          else if (pos.size() >= 3) {
              bool flag = true;
              for (int j = 1; j < pos.size(); ++j) {
                  if (pos[i + 1] - pos[i] != 2) { // 모든 인덱스가 전부 2 차이어야 함
                      flag = false;
                      break;
                  }
              }
              if (flag) // 이곳에 해당
                  continue;
          }
          // 3. 위 두 경우를 제외한 나머지 경우들은 다음 문자인 소문자가 전부 규칙 2 혹은 규칙 1+2 단어의 특수문자가 되어야 한다. ex) OaOOa, OaObOa, ObOb
          else {
              first_rule = false; // // 규칙 1 OFF
              words.push_back(word); // // 단어 추가
              word = ""; / 리셋
          }
          }
          
현재 문자가 소문자일 때 : if (islower(sentence[i]))

현재 아무런 규칙 상태가 아닌데 현재 문자가 소문자라면 규칙 2 에 해당하는 단어가 시작된다는 것이다.

  • 현재 문자는 단어의 첫 소문자이니 사용 여부 체크
    • 다른 단어에 사용된적이 있다면 “invalid”
                    if (checked[sentence[i] - 'a'])
                      return invalid;
      
  • 다음 문자가 범위를 넘어설 때 ex) a
    • 규칙 2 단어가 시작되야 하는데 이대로 끝나는 것이므로 “invalid”
                    if (i + 1 == sentence.length())
                      return invalid;
      
  • 다음 문자가 소문자일 때 ex) ab
    • 규칙 2 의 소문자 두 개는 대문자 단어들을 감싸야 한다. 따라서 소문자가 연달아 나올 수 없다.
                    else if (islower(sentence[i + 1]))
                      return invalid;
      
  • 현재 문자는 규칙 2 단어의 첫 특수문자가 된다.
                  second_rule = true;
                  char_rule2 = sentence[i];
    


2️⃣ 오직 규칙 1 상태일 때 : else if (first_rule)


이 부분의 전체 코드 펼쳐서 확인하기 Click ✨
        else if (first_rule) {
            if (isupper(sentence[i])) {
                word += sentence[i];

                if (i + 1 == sentence.length()) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;
                    words.push_back(word);
                    word = "";
                }
                else if (isupper(sentence[i + 1])) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;
                    words.push_back(word);
                    word = "";
                }
                else if (char_rule1 != sentence[i + 1]) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;
                    words.push_back(word);
                    word = "";
                }
            }
            if (islower(sentence[i])) {
                if (i + 1 == sentence.length())
                    return invalid;
                else if (islower(sentence[i + 1]))
                    return invalid;
            }
        }

현재 문자가 대문자일 때 : if (isupper(sentence[i]))

규칙 1 상태일 때 현재 문자가 대문자라면 규칙 1 에 해당하는 단어의 문자라는 것이다. 또한 현재 규칙 1 상태인데 현재 문자가 대문자라면 규칙 1 에 해당하는 단어의 마지막 문자일 수 있는 후보가 된다.

  • 현재 문자는 규칙 1 단어의 문자가 된다.
    word += sentence[i];
    
  • 다음 문자가 범위를 넘어설 때 ex) PaP
    • 즉, sentence의 마지막 문자일 때다. 그러니 하나의 단어가 끝난 셈이다.
    • 한 단어가 바로 끝났으니 OFF 해준다.
      if (i + 1 == sentence.length()) {
          first_rule = false; // 규칙 1 OFF
          checked[char_rule1 - 'a'] = true; // 이제 다른 새 단어에서 이번 규칙 1 에 쓰인 소문자(특수문자)를 다신 쓸 수 없도록 체크
          char_rule1 = NULL; // 리셋
          words.push_back(word); // 단어 추가
          word = ""; // 리셋
      }
      
  • 다음 문자가 대문자일 때 ex) PaPP
    • 하나의 단어가 끝낸 셈이다.
    • 한 단어가 바로 끝났으니 OFF 해준다.
      else if (isupper(sentence[i + 1])) {
          first_rule = false; // 규칙 1 OFF
          checked[char_rule1 - 'a'] = true; // 이제 다른 새 단어에서 이번 규칙 1 에 쓰인 소문자(특수문자)를 다신 쓸 수 없도록 체크
          char_rule1 = NULL; // 리셋
          words.push_back(word); // 단어 추가
          word = ""; // 리셋
      }
      
  • 다음 문자가 소문자인데 현재 규칙의 특수문자가 아닐 때 ex) PaPb
    • 하나의 단어가 끝낸 셈이다.
    • 한 단어가 바로 끝났으니 OFF 해준다.
      else if (char_rule1 != sentence[i + 1]) {
          first_rule = false; // 규칙 1 OFF
          checked[char_rule1 - 'a'] = true; // 이제 다른 새 단어에서 이번 규칙 1 에 쓰인 소문자(특수문자)를 다신 쓸 수 없도록 체크
          char_rule1 = NULL; // 리셋
          words.push_back(word); // 단어 추가
          word = ""; // 리셋
      }
      
현재 문자가 소문자일 때 : if (islower(sentence[i]))

규칙 1 상태일 때 현재 문자가 소문자라면 규칙 1 의 특수문자라는 것이다

  • 다음 문자가 범위를 넘어설 때 ex) Pa, PaPaPa
    • 규칙 1 은 대문자로 끝나야 하는데 끝나버린 것이므로 invalid
      if (i + 1 == sentence.length())
          return invalid;
      
  • 다음 문자가 소문자일 때 ex) Pab, PaPaPab
    • 규칙 1 은 소문자가 연달아 나올 수 없으므로 invalid
      else if (islower(sentence[i + 1]))
          return invalid;
      


3️⃣ 오직 규칙 2 상태일 때 : else if (second_rule)


이 부분의 전체 코드 펼쳐서 확인하기 Click ✨
        else if (second_rule) {
            if (isupper(sentence[i])) {
                word += sentence[i];

                if (i + 1 == sentence.length())
                    return invalid;
                else if (islower(sentence[i + 1]) && char_rule2 != sentence[i + 1]) {
                    if (char_rule2 == sentence[i - 1]) {
                        if (checked[sentence[i + 1] - 'a'])
                            return invalid;
                        first_rule = true;
                        char_rule1 = sentence[i + 1];
                    }
                    else
                        return invalid;
                }
            }
            if (islower(sentence[i])) {
                second_rule = false;
                checked[char_rule2 - 'a'] = true;
                char_rule2 = NULL;
                words.push_back(word);
                word = "";
            }
        }

현재 문자가 대문자일 때 : if (isupper(sentence[i]))

규칙 2 상태일 때 현재 문자가 대문자라면 규칙 2 에 해당하는 단어의 문자라는 것이다.

  • 현재 문자는 규칙 2 단어의 문자가 된다.
    word += sentence[i];
    
  • 다음 문자가 범위를 넘어설 때 ex) aP
    • 규칙 2 단어는 시작했을 때의 그 소문자로 소문자로 끝나야 한다. aPPPa 꼴! 대문자로 끝날 수 없다.
      if (i + 1 == sentence.length())
          return invalid;
      
  • 다음 문자가 소문자이고 규칙 2 단어의 특수문자가 아닌 새로운 특수문자일 때 *ex) aPb, aPPPb
    else if (islower(sentence[i + 1]) && char_rule2 != sentence[i + 1])
    
    • ⭐바로 현재 문자(대문자)의 이전 문자가 규칙 2 단어의 특수문자라면 한 단어에 규칙 1 + 2 짬뽕이 적용되기 시작된 것이다.aPbPbPa 같은! ex) aPb
      • 현재 규칙 2 인 상태이니 규칙 1 도 ON 해주면 된다.
                      if (char_rule2 == sentence[i - 1]) {
                          // 다음 문자는 규칙 1 단어의 첫 소문자이니 방문 체크 (이미 이전 단어에서 쓰인적이 있는 특수문자인지)
                          if (checked[sentence[i + 1] - 'a'])
                              return invalid;
                          first_rule = true; // 규칙 1 ON
                          char_rule1 = sentence[i + 1]; // 다음 문자는 현재 단어의 특수문자
                      }
        
    • 아니라면 “invalid” ex) aPPPb
                      else
                          return invalid;
      
현재 문자가 소문자일 때 : if (islower(sentence[i]))

규칙 2 상태일 때 현재 문자가 소문자라면 규칙 2 가 종료된다는 것이다. 다음 문자가 새로운 소문자라면 invalid 되도록 “현재 문자가 대문자일 때” 에서 모두 걸러냈다. 그러므로 현재 문자가 소문자인 경우는 기존 규칙 2 특수문자인 경우다. *ex) aOOOa

            if (islower(sentence[i])) {
                second_rule = false;
                checked[char_rule2 - 'a'] = true;
                char_rule2 = NULL;
                words.push_back(word);
                word = "";
            }


2️⃣ 규칙 1 and 2 상태일 때 : if (first_rule && second_rule)


이 부분의 전체 코드 펼쳐서 확인하기 Click ✨
        if (first_rule && second_rule) {
            if (isupper(sentence[i])) {
                word += sentence[i];

                if (i + 1 == sentence.length())
                    return invalid;
                else if (isupper(sentence[i + 1]))
                    return invalid;
                else if (char_rule1 != sentence[i + 1] && char_rule2 != sentence[i + 1])
                    return invalid;
            }
            if (islower(sentence[i])) {
                if (char_rule2 == sentence[i]) {
                    first_rule = false;
                    checked[char_rule1 - 'a'] = true;
                    char_rule1 = NULL;

                    second_rule = false;
                    checked[char_rule2 - 'a'] = true;
                    char_rule2 = NULL;

                    words.push_back(word);
                    word = "";

                    continue;
                }
                if (i + 1 == sentence.length())
                    return "invalid";
                else if (islower(sentence[i + 1]))
                    return "invalid";
            }
        }

현재 문자가 대문자일 때 : if (isupper(sentence[i]))

규칙 1+2 상태일 때 현재 문자가 대문자라면 규칙 1+2 에 해당하는 단어의 문자라는 것이다.

  • 현재 문자는 규칙 1+2 단어의 문자가 된다.
    word += sentence[i];
    
  • 다음 문자가 범위를 넘어설 때 ex) aPbP
    • 규칙 1+2 단어는 시작했을 때의 그 소문자로 소문자로 끝나야 한다. aPbPa 꼴! 대문자로 끝날 수 없다.
      if (i + 1 == sentence.length())
          return invalid;
      
  • 다음 문자가 대문자일 때 ex) aPbPP
    • 규칙 1+2 단어는 대문자 사이 사이에 소문자가 와야 한다. 대문자가 연달아나올 수 없다.
      else if (isupper(sentence[i + 1]))
          return invalid;
      
  • 다음 문자가 소문자인데 현재 규칙의 특수문자가 아닐 때. 규칙 1 특수문자도, 규칙 2 특수문자도 아닌 완전히 새로운 특수문자 ex) aPbPc
    • 규칙 1+2 단어는 규칙 2 특수문자로 끝나야 한다.
      else if (char_rule1 != sentence[i + 1] && char_rule2 != sentence[i + 1])
          return invalid;
      
현재 문자가 소문자일 때 : if (islower(sentence[i]))

규칙 1+2 단어에서 소문자가 등장했다면 종료하는 소문자(규칙2)인지 그냥 사이 사이에 끼어 있는 소문자(규칙1)인지 구분해야 한다. 전자면 규칙 1+2 단어를 종료시켜야 하고 후자면 딱히 할게 없다.

  • 현재 문자가 규칙 2 특수문자일 때 ex) aPbPa
    • 두 규칙을 OFF 시키고 단어 추가
                  if (char_rule2 == sentence[i]) {
                      first_rule = false;
                      checked[char_rule1 - 'a'] = true;
                      char_rule1 = NULL;
      
                      second_rule = false;
                      checked[char_rule2 - 'a'] = true;
                      char_rule2 = NULL;
      
                      words.push_back(word);
                      word = "";
      
                      continue;
                  }
      
  • 현재 문자가 규칙 2 특수문자도 아니고 다음 문자가 범위를 넘어설 때 ex) aPbPb
    • 규칙 1+2 단어는 시작했을 때의 그 소문자로 소문자로 끝나야 한다. aPbPbPa 꼴!
      if (i + 1 == sentence.length())
          return invalid;
      
  • 다음 문자가 소문자일 때 ex) aPbPbb
    • 규칙 1+2 단어는 대문자 사이 사이에 소문자가 와야 한다. 소문자가 연달아나올 수 없다.
      else if (islower(sentence[i + 1]))
          return invalid;
      


🌜 개인 공부 기록용 블로그입니다. 오류나 틀린 부분이 있을 경우 
언제든지 댓글 혹은 메일로 지적해주시면 감사하겠습니다! 😄

맨 위로 이동하기

Programmers 카테고리 내 다른 글 보러가기

댓글 남기기