[프로그래머스] 코딩 테스트 입문 - 컨트롤 제트(Java)

수경·2022년 11월 12일
0

problem solving

목록 보기
57/174

프로그래머스 - 컨트롤 제트

문제

숫자들이 공백으로 구분된 문자열이 주어집니다. 문자열에 있는 숫자를 차례대로 더하려고 합니다. 이 때 “Z”가 나오면 바로 전에 더했던 숫자를 뺀다는 뜻입니다. 숫자와 “Z”로 이루어진 문자열 s가 주어질 때, 머쓱이가 구한 값을 return 하도록 solution 함수를 완성해보세요.

❗️제한 사항

  • 0 < s의 길이 < 1,000
  • -1,000 < s의 원소 중 숫자 < 1,000
  • s는 숫자, "Z", 공백으로 이루어져 있습니다.
  • s에 있는 숫자와 "Z"는 서로 공백으로 구분됩니다.
  • 연속된 공백은 주어지지 않습니다.
  • 0을 제외하고는 0으로 시작하는 숫자는 없습니다.
  • s의 시작과 끝에는 공백이 없습니다.
  • 모든 숫자를 지우는 경우는 주어지지 않습니다.
  • 지울 숫자가 없는 상태에서 "Z"는 무시합니다.

입출력 예시

sresult
"1 2 Z 3"4
"10 20 30 40"100
"10 Z 20 Z 1"1

풀이

  1. 입력받은 배열 s의 공백을 제거한 후 ArrayList타입 변수 items으로 저장
  2. 만약 items에 "Z"가 있으면 해당 요소와 그 직전 요소 삭제
  3. items를 순회하며 모든 값을 더한 후 반환

삽질

  1. 풀이 2번까지 한 후에 Iterator를 사용해서 순회했는데 ConcurrentModificationException 이 발생했다. 구글링 결과, ArrayList에서 remove()를 호출할 때 length가 변경되고 인덱스 값이 null로 변경돼서 오류가 발생한 것이었다. 해결하기 위해서는 ArrayList에서 직접 remove를 하는 대신 iterator에서 remove를 해야 한다.

  2. iterator에서 remove를 하는 방식으로 코드를 갈아 엎었다. 풀이 2번 과정을 빼고 바로 순회하는 거였는데, iterator로 순회를 하게 되면 다음 값을 읽어오는 메소드 iterator.next() 만 사용할 수 있게 돼서 "Z"를 만났을 때 그 전의 요소 값을 알지 못해 삭제하지 못하게 된다. (배열로 저장해서 for문으로 인덱스에 접근하면 뭐 할 수는 있겠지만,,, ArrayList를 사용하고 싶었고, ArrayList로도 물론 할 수 있겠지만 굳이..? 싶었다 ㅎ)

  3. 결국 iterator로 순회하는 것을 빼고 for문으로 인덱스에 접근하는 방식을 선택함. ArrayList는 아예 iterator로만 순회해야 하는 줄 알았는데 잘만 돌아갔다. 생각해보니까 Collection 자체를 iterator로 순회해야 하고, ArrayList는 연속된 메모리에 저장돼서 잘 돌아가는 것 같다. 왜 이걸 몰랐지?


코드

import java.util.ArrayList;
import java.util.Arrays;

public class ControlZ {
    public int solution(String s) {
        ArrayList<String> items = new ArrayList<>(Arrays.asList(s.split(" ")));
        String z = "Z";
        int sum = 0;

        while (items.contains(z)) {
            items.remove(items.indexOf(z) - 1);
            items.remove(items.indexOf(z));
        }
        for (int i = 0; i < items.size(); i++)
            sum += Integer.parseInt(items.get(i));
        return sum;
    }

    public static void main(String[] args) {
        ControlZ controlZ = new ControlZ();
        System.out.println(controlZ.solution("1 2 Z 3"));		// 4
        System.out.println(controlZ.solution("10 20 30 40"));	// 100
        System.out.println(controlZ.solution("10 Z 20 Z 1"));	// 1
    }
}

컬렉션 프레임워크를 배우고 코테 문제에 처음 사용해봤는데 어려운 과제가 아닌데도 훨씬 편하다는 걸 벌써 알겠다ㅠㅠ 역시 자바 불친절해도 이런건 해주는 구나... 정말 다행^^~ 앞으로 더 많이 자주 써서 완전히 익혀야지!

profile
어쩌다보니 tmi뿐인 블로그😎

0개의 댓글