Troubleshooting: 무엇이 문제였는가?/본캠프 2주 차: 키오스크 만들기

3단계: "Field can be converted to a local variable"

writingforever162 2024. 11. 25. 19:54

[문제]

package com.example.kiosk.level3;
// Kiosk 클래스
import java.util.*;

public class Kiosk {
    Scanner sc = new Scanner(System.in);
    List<MenuItem> menuItems = new ArrayList<>();
    private int index;
    // [문제] 위의 코드 두 줄에서 노란 전구가 깜빡였다.

    public Kiosk(List<MenuItem> menuItems) {
        this.menuItems = menuItems;
    }

    public void start() {
        for (index = 0; index < this.menuItems.size(); index++) {
            this.menuItems.get(index).getMenuInfo(index + 1);
        }
        System.out.println("0. 종료           | 종료");

        while (true) {
            System.out.println();
            System.out.println("메뉴판에서 원하는 햄버거 번호를 입력해 주세요.");
            System.out.print("만약 종료를 원하신다면 0을 입력해 주세요: ");
            index = sc.nextInt();

            if (index >= 5 || index == 0) {
                System.out.println("메뉴 번호 외에 다른 숫자를 입력했습니다. 프로그램을 종료합니다.");
                break;
            } else {
                System.out.println();
                menuItems.get(index - 1).getEachItem();
            }
        }
    }
}

프로그램을 실행하는 데에는 문제가 없었으나, 노란 경고 두 개가 영 신경 쓰여서 튜터님께 달려갔다. 멤버 변수로 선언한 'private int index;' 부분을 커서(cursor)로 가리키면 'Field can be converted to a local variable'이라는 문구가 떴다. 필드에 멤버 변수로 선언한 변수를 로컬 변수로 바꿔도 된단 뜻이었다. 의미는 이해했으나 궁금한 점은 그런 제안을 '왜' 하는지였다.

 

[원인]

package com.example.kiosk.level3;

import java.util.*;

public class Kiosk {
    Scanner sc = new Scanner(System.in);
    List<MenuItem> menuItems = new ArrayList<>();
    private int index;

    public Kiosk(List<MenuItem> menuItems) {
        this.menuItems = menuItems;
    }

    public void start() {
    // [원인] start() 메서드 안에서만 해당 변수가 쓰였기 때문에!
        for (index = 0; index < this.menuItems.size(); index++) {
            this.menuItems.get(index).getMenuInfo(index + 1);
        }
        System.out.println("0. 종료           | 종료");

        while (true) {
            System.out.println();
            System.out.println("메뉴판에서 원하는 햄버거 번호를 입력해 주세요.");
            System.out.print("만약 종료를 원하신다면 0을 입력해 주세요: ");
            index = sc.nextInt();

            if (index >= 5 || index == 0) {
                System.out.println("메뉴 번호 외에 다른 숫자를 입력했습니다. 프로그램을 종료합니다.");
                break;
            } else {
                System.out.println();
                menuItems.get(index - 1).getEachItem();
            }
        }
    }
}

원인은 클래스 속성으로 선언한 변수를 start() 메서드 안에서만 사용한 데에 있었다. 정수형 int 타입 변수 index를 멤버 변수로 선언해 놓고는 막상 로컬 변수(local variable, == 지역 변수)로 사용하니 프로그램이 '굳이 그럴 필요가 있어'라고 물어본 거라고.

 

[해결]

package com.example.kiosk.level3;
// Kiosk 클래스
import java.util.*;

public class Kiosk {
    Scanner sc = new Scanner(System.in);
    List<MenuItem> menuItems = new ArrayList<>();
    // [수정 전] private int index;
    // [수정 후] 삭제

    public Kiosk(List<MenuItem> menuItems) {
        this.menuItems = menuItems;
    }

    public void start() {
        int index;
        // [수정 전] 없었음
        // [수정 후] start() 메서드 안에서 정수형 int 타입 변수 index 선언
        for (index = 0; index < this.menuItems.size(); index++) {
            this.menuItems.get(index).getMenuInfo(index + 1);
        }
        System.out.println("0. 종료           | 종료");

        while (true) {
            System.out.println();
            System.out.println("메뉴판에서 원하는 햄버거 번호를 입력해 주세요.");
            System.out.print("만약 종료를 원하신다면 0을 입력해 주세요: ");
            index = sc.nextInt();

            if (index >= 5 || index == 0) {
                System.out.println("메뉴 번호 외에 다른 숫자를 입력했습니다. 프로그램을 종료합니다.");
                break;
            } else {
                System.out.println();
                menuItems.get(index - 1).getEachItem();
            }
        }
    }
}

이제 남은 노란 전구는 딱 하나였다. (링크: 남은 노란 줄을 없앤 과정)

 

[수정 전] 자바(Java) 인텔리제이(IntelliJ) 노란 줄 경고 표시 2개 발생

[수정 후] 자바(Java) 인텔리제이(IntelliJ) 노란 줄 경고 표시 1개 발생