[Java] 조건문과 메서드 오버로딩

Yunhye Park·2024년 1월 23일
0
post-thumbnail
post-custom-banner

자바스크립트만 진득히 배우다가 처음으로 자바를 알아가기 시작했다. 기본 문법은 JS와 크게 다르지 않다고 느꼈는데, 조건문 예제를 풀면서 은근히 다르다는 걸 알게 되었다.

예제 1 : 조건문

a를 입력했을 때 '홀수', b를 입력했을 때 '짝수', 그 외 값 입력 시 '모르겠어요.' 출력하기

1. if else 문

자바는 main 메서드에서 실행해서 불러온 후에 Scanner를 불러와 입력을, sout으로 출력을 해준다.

package _02_conditional;

import java.util.Scanner;

public class ConditionalPrac1 {
    public static void main(String[] args) {
        System.out.println("영어 소문자를 입력하세요.");
        Scanner sc = new Scanner(System.in);
        String name = sc.next();

        // if else 문
        if(name.equals("a")) {
            System.out.println("홀수");
        } else if (name.equals("b")) {
            System.out.println("짝수");
        } else {
            System.out.println("모르겠어요.");
        }
    }
}

String 타입은 기본형 같이 보여도 참조형이란 걸 나름 티내기 위해(?) 대문자로 시작한다. 그래서 문자열을 비교할 때 연산자 ===가 아니라 .equals() 메서드를 사용한다.

그외 if문 자체에는 별 특이점이 없다.

2. switch case 문

issue 1

  • 상황 : return System.out.println(~~)에 아래와 같은 오류 메시지
Cannot return a value from a method with void result type
  • 원인 : 출력은 그냥 콘솔에 찍는 것과 같아서 무언가를 반환하는 게 아니다. 그래서 return하는 타입이 void라는 오류를 보여준 것이다.
  • 해결 : 출력은 반환값이 없으므로 return 없이 sout

issue 2

  • 상황 : const 키워드 사용했더니 Unexpected token
  • 원인 : Java에는 const, let 키워드가 없다.
  • 해결 : var 키워드 혹은 final 키워드를 사용.

    final 키워드
    final 키워드는 변수, 클래스, 메서드 모두에서 사용할 수 있는데 제약을 건다는 느낌이다. 예를 들어, 변수로 사용하는 final 키워드는 변수 '값'을 바꿀 수 없다. 즉 변수를 상수로 사용할 때 쓴다.

JDK 12부터 간결한 문법이 허용된다. 그 자체로 값을 리턴하기에 곧장 변수에 담을 수 있다. 마치 JS의 배열 메서드 map, filter, find처럼!

// Var
		var nameResult = switch (name) {
            case "홍길동" -> "man";
            case "성춘향" -> "woman";
            default -> "모르겠어요.";
        };
        
        System.out.println(nameResult);
// Final
        final String nameResult = switch (name) {
            case "홍길동" -> "man";
            case "성춘향" -> "woman";
            default -> "모르겠어요.";
        };
        
        System.out.println(nameResult);

final 키워드는 변수의 데이터 타입까지 명시해줘야 한다. 자바는 강한 데이터 타입임을 생각하면 var보다 final을 권장하려나 싶었는데 둘의 쓰임이 다르댄다.

  • final : 변수를 상수로 만들 때
  • var : 지역 변수의 타입을 추론할 때

    var 보충 설명
    변수를 선언할 때 명시적으로 타입을 지정하지 않고, 컴파일러가 변수 초기값으로 타입을 추론한다.
    지역 변수일 때만 사용 가능해서 객체의 필드(객체 상태를 나타내는 변수)나 메서드 매개변수에서는 사용 불가.

이어서 자바스크립트엔 없던 오버로딩 개념도 배웠다.

예제 2 : 메서드 오버로딩

동일한 메서드명으로 원의 넓이, 직사각형의 넓이, 삼각형의 넓이 구하기

생각할 점은 아래와 같다.

  1. 메서드 만들기
  2. 동명의 메서드에 타입까지 같다면 어떻게 차이를 만들 것인가
  3. 연산값은 실수인데 문자열은 정수

메서드

자바는 객체 지향 프로그램으로, 모든 것이 객체로 이루어진다. 그래서 new 키워드로 클래스의 생성자를 호출하여 객체를 생성하고, 그 객체의 인스턴스를 통해 메서드를 호출하는 등 동작을 수행한다.

메서드 정의

[접근 제어자] [반환 타입] [메서드 이름]([매개변수 목록]) {
    // 메서드의 내용
}
  • 접근 제어자 :
    자바의 접근 제어자는 크게 4가지이지만 간단히 둘로 나눌 수도 있겠다. 모든 패키지에서 사용하려면 public을, 이 패키지 내에서만 사용해도 된다면 private을 입력한다. 후자의 경우 생략도 가능하다.
  • 반환 타입 :
    반환하지 않으면 void, 반환한다면 return하는 내용에 맞춰 타입을 입력하면 된다.
  • 메서드 이름 :
    오버로딩을 할 거라면 동명의 이름을 짓는다.
  • 매개변수 목록 :
    매개변수의 타입이 다르거나 개수가 다르면 메서드 오버로딩이 가능하다.
package _02_conditional;

public class MethodPrac1 {
    public static void main(String[] args) {
        MethodPrac1 ol = new MethodPrac1();

        ol.area(5);
        ol.area(4, 7);
        ol.area(6,3, true);
    }
}

클래스(MethodPrac1)의 생성자를 호출하여(new MethodPrac1()) 'ol'이라는 객체를 만들었다.

여기에 area라는 메서드를 타고 들어가(.) 불러오고자 하는 메서드의 매개변수에 맞게 값을 기입했다.

정의한 메서드는 아래와 같다.

    void area(int r) {
        System.out.printf("반지름이 %d인 원의 넓이: %f",
        r, Math.PI * r * r).println();
    };

    void area(int w, int h) {
        double convertedWH = w * h;
        System.out.printf("가로 %d, 세로 %d인 직사각형의 넓이: %.1f",
        w, h, convertedWH).println();
    };
    void area(int a, int h, boolean isTriangle) {
        System.out.printf("밑변 %d, 높이 %d인 삼각형의 넓이: %.1f",
        a, h, 0.5 * a * h).println();
    };

sout로 출력만 해서 반환값이 없다. 그래서 반환 타입은 void.

매개변수 개수 혹은 타입이 달라야 하는데 주어진 문제는 모두 정수를 매개변수로 받는다. 그래서 두번째와 세번째 매개변수는 타입과 개수가 동일하다. 그럼에도 달라야 하니까 새로운 매개변수를(isTriangle) 넣어준다.

정수를 받아와서 실수 형식으로 출력하니까 형식 지정자를 사용해야 한다. 그러려면? printf를 쓰거나 println에서 String.format 메서드를 사용한다.

printf와 println

  • printf : 형식 지정자를 사용해 문자열을 지정된 형식으로 출력
  • println : 문자 출력 메서드로 개행(\n) 함

형식지정자
%d : 정수 형식 지정자 (10진수)
%f : 부동 소수점 형식 지정자
%s : 문자열 형식 지정자

부동 '소수점'은 그 이름에서 보이듯 소수점 자리를 결정할 수도 있다. 예제 첫번째는 딱히 제한이 없어보이는데 두 세번째는 소수점 한 자리까지(%.1f)만 출력한다.

문자열 안에 형식 지정자를 정의("가로 %d, 세로 %d인 직사각형의 넓이: %.1f")하고, 정의한 순서대로 해당하는 매개변수를 순차적으로 나열(w, h, )한 후 원하는 연산을 이어간다.

System.out.printf("가로 %d, 세로 %d인 직사각형의 넓이: %.1f",
        w, h, convertedWH).println();

그런데 직사각형은 연산에 소수점이 들어올 일이 없다. 정수끼리 곱해봤자 정수이지, 실수가 되지 못한다. 그래서 형변환을 해줘야겠다.

형변환

작은 범위에서 큰 범위로 형변환할 땐 데이터 손실이 일어나지 않으므로 암시적 형변환을, 반대의 경우는 데이터 손실이 발생할 수 있으므로 명시적 형변환을 해준다.

  • 암시적 형변환
double convertedWH = w * h;

값을 할당하듯 적어준다.

  • 명시적 형변환
(double) x * y

변환할 것 앞에 (타입)을 붙여준다.

큰 따옴표와 작은 따옴표

자바스크립트에서는 상관도 없던 것이.. 자바에서는 타입에 따라 명확히 구분된다.

  • 작은 따옴표 : char
  • 큰 따옴표 : String
profile
일단 해보는 편
post-custom-banner

0개의 댓글