SyntaxHighlighter.all(); 'Java' 카테고리의 글 목록 (2 Page) :: 게을러지고 싶어 부지런한 개발자

 

방법1)

 char - '0'을 이용하면 아스키코드값을 알 필요없이 int형으로 변환 가능
 

방법2)

 Character.getNumericValue(input.charAt(i)) 방법을 이용해도 형변환이 가능

 

 

 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
 
// 1234567을 입력받으면 결과는 1+2+3+4+5+6+7=28출력
public class Main   {
    public static void main(String[] args) throws Exception {
        
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        
        String input = br.readLine();
        
        int sum = 0
        
        for (int i = 0; i < input.length(); i++) {
            // sum += input.charAt(i) - '0';  // 방법 1
            sum += Character.getNumericValue(input.charAt(i));  //방법 2
        }
        
        System.out.println(sum);
    }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
public class Test {
 
    public static void main(String[] args) {
        String str = "Hello Java!!";
        System.out.println("str: " + str);
        
        StringBuilder sb = new StringBuilder();
        
        for (int j = 0; j < str.length(); j++) {
            sb.append(str.charAt(j));
        }
        
        System.out.println("sb: " + sb);
    }
}

<출력결과>

 

str: Hello Java!!

sb: Hello Java!! 

HashMap을 사용할 때 알아두면 유용한 메소드를 오늘 새로 하나 배웠다. 

 

 

getOrDefault() : 찾는 키가 존재하면 해당 키의 값을 반환하고, 없으면 기본값을 반환함 

 

 

map.put(키, 값) 

--> map.put(a라는 키, a의 값이 존재하면 a의 값을 넣어주고 없다면 0)  , 그리고 + 1 

 

 

<자바의정석 3판, Ch2 내용 중> 

 

변수의 타입은 크게 기본형 & 참조형로 나눔 

기본형(Primitive type)

실제 값(data)을 저장   

<총 8개>

-문자형(char)

-정수형(byte, short, int, long)

-실수형(float, double)

-논리형(boolean) 

참조형(Reference type) 객체의 주소를 저장 . 8개의 기본형 제외한 나머지

 

기본형에서 boolean을 제외한 나머지 타입들은 서로 형변환이 가능 

-하지만 기본형 <-> 참조형은 서로 형변환 할 수 없음 (참조형의 형변환은 자바-Ch7에 설명) 

변환 방법:   (타입)피연산자

 

정수형에서 실수형으로 변환:

  • 실수형이 정수형보다 훨씬 큰 저장범위 갖기에 정수형-> 실수형 변환에 별 무리가 X
  • 한 가지 주의할 점: float는 약 7자리의 정밀도만을 제공하므로, 8자리 이상의 정수값을 실수형으로 변환할 때는 float이 아닌 약 15자리의 정밀도를 갖는 double로 형변환해야 오차 발생 안함                                            

Ex.

int형 12345678를 float으로 변환  → 12345679.0

int형 12345678를 double로 변환 → 12345678.0

 

실수형을 정수형으로 변환 

  • 실수형의 소수점 이하 값은 버려짐(자료의 손실 발생 가능) 
  • 반올림 발생 X  (ex. 실수 1.666 를 int로 형변환하면, 1이 됨) 

 

자동 형변환

: 서로 다른 타입의 변순간의 연산은 형변환을 하는 것이 원칙이지만,

값의 범위가 작은 타입에서 큰 타입으로의 형변환은 생략 가능 

(컴파일러가 생략된 형변환을 자동적으로 해줌) 

 

ex) int i = 3; 

     double d = 1.0 + i;    //double d = 1.0 + (double)i; 에서 형변환 생략됨 

 

 

 

 

기본형타입 간 형변환 예시 

class Main {
	
	public static void main(String[] args) {
		int i = 12345678; 
		float f = (float)i;  //int를 float으로 형변환
		int i2 = (int)f; 	 //float를 다시 int로 형변환
		
		double d = (double)i; //int를 double로 형변환
		int i3 = (int)d;      //double를 다시 int로  형변환 	
		System.out.println(i);   //출력:  12345678
		System.out.println(f);   //출력: 12345679.0
		System.out.println(i2);  //출력: 12345679
	
		System.out.println(d);	 //출력: 12345678.0
		System.out.println(i3);  //출력: 1234568
	}
}

 

숫자로 이루어진 문자열을 숫자로, 또는 그 반대로 변환하는 경우가 자주 있음.


●기본형 값을 String으로 변환


두가지 방법이 있음. 


(1) 숫자에 빈 문자열 ""을 더해주기

또는

(2) valueOf() 사용 

(성능은 valueOf()가 더 좋지만, 빈 문자열을 더하는 방법이 간단하고 편하기 때문에 성능향상이 필요한 경우에만 valueOf()를 쓰자. )


1
2
3
int i = 100;
String str1 = i + "";                //100을 "100"으로 변환하는 방법1
String str2 = String.valueOf(i);    //100을 "100"으로 변환하는 방법1
cs




●String을 기본형 값으로 변환 


반대로 String을 기본형으로 변환하는 방법도 간단함.


(1) parseInt() 사용

또는 

(2) valueOf() 사용 


1
2
3
int i1 = Integer.parseInt("100");    //"100"을 100으로 변환하는 방법1
int i2 = Integer.valueOf("100");    //"100"을 100으로 변환하는 방법2
 
cs




기본형과 문자열간의 변환방법을 정리하면 다음과 같다. 

 기본형 -> 문자열

문자열 -> 기본형 

String String.valueOf(boolean b)

String String.valueOf(char b)

String String.valueOf(int b)

String String.valueOf(long b)

String String.valueOf(float b)

String String.valueOf(double b)

boolean Boolean.parseBoolean(String s)
byte Byte.parseBoolean(String s)
short Short.parseBoolean(String s)
int Integer.parseBoolean(String s)
long long .parseBoolean(String s)
float Float.parseBoolean(String s)
double Double .parseBoolean(String s)


예외 & 예외처리란? 


예외(Exception): 프로그램에 문제가 있는 것.

예외처리(Exception handling): 예외로 인해 시스템 동작이 멈추는 것을 막는 것 



계층구조 


예외 클래스 계층도


계층구조 - Throwable 클래스 


Throwable 클래스: 모든 예외의 조상이 되는 Exception 클래스와 모든 오류의 조상이 되는 Error 클래스의 부모 클래스


-이 클래스에는 예외나 오류에 관한 다양한 정보를 확인할 수 있는 다음과 같은 메소드가 포함됨 

메소드설명
String getMessage()해당 throwable 객체에 대한 자세한 내용을 문자열로 반환함.
void printStackTrace()해당 throwable 객체와 표준 오류 스트림(standard error stream)에서 해당 객체의 스택 트레이스(stack trace)를 출력함.
String toString()해당 throwable 객체에 대한 간략한 내용을 문자열로 반환함.


계층구조 - Exception 클래스의 두 하위클래스

 

1. RuntimeException 클래스

2. 그 외의 Exception 클래스의 자식 클래스



1) RuntimeException클래스들: 주로 프로그래머의 실수로 발생하는 예외 

RuntimeException 클래스를 상속받는 자식 클래스들은 주로 치명적인 예외 상황을 발생시키지 않는 예외들로 구성됨

따라서 try / catch 문을 사용하기보다는 프로그램을 작성하면서 예외가 발생하지 않도록 주의를 기울이는 편이 좋음.

이처럼 예외처리를 개발자의 판단에 맞기는 경우 (ex. 데이터 오류 등), Unchecked Exception 라고 함 


ex)

- ArrayIndexOutOfBoundException: 배열에서 존재하지 않는 인덱스 가리킬때

- ArithmeticException: 정수를 0으로 나누려고 하는 경우

- ClassCastException: 클래스간의 형변환을 잘못한 경우 

- NumberFormatException: 숫자데이터 문제데이터 등을 넣었을 때

- NullPointerException: null 객체의 레퍼런스를 이용하거나 null 객체의 인스턴스 메소드를 호출하는 등 



2) Execption클래스들: 사용자의 실수와 같은 외적인 요인에 의해 발생하는 예외  

(RuntimeException클래스들을 제외한 나머지 클래스들)

 

 RuntimeException클래스들 이외의 Exception 클래스에 속하는 자식 클래스들은 치명적인 예외 상황을 발생시키므로, 반드시 try / catch 문을 사용하여 예외를 처리해야만 함. 이처럼 예외처리를 반드시 해야하는 경우는 (ex. 네트워크, 파일 시스템, 파일 입출력 등) Checked Exception라고 함 


ex) 


-ClassNotFoundException: 실수로 클래스의 이름을 잘못 적은 경우

-DataFormatException: 입력한 데이터 형식이 잘못된 경우

-FileNotFoundException: 존재하지 않는 파일의 이름 입력 시  





예외처리 방법


1. try-catch-fianally : 예외 발생 시 개발자가 알아서 해결


-catch문과 finally문은 선택(옵션)이므로 반드시 작성할 필요는 없음 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
try {
 
    예외를 처리하길 원하는 실행 코드;
 
catch (e1) {
 
    e1 예외가 발생할 경우에 실행될 코드;
 
catch (e2) {
 
    e2 예외가 발생할 경우에 실행될 코드;
 
}
 
...
 
finally {
 
    예외 발생 여부와 상관없이 무조건 실행될 코드;
 
}
cs



●어떤 예외가 발생했는지 알기 위해 사용하는 메소드들 

(Throwable클래스를 상속받고 있으므로 바로 호출가능) 


 e.printStackTrace();   :   어떤 예외 발생했는지 콘솔에 출력    ex) java.lang.ArithmeticException: / by zero

 e.getMessage();        :   예외 간략히 나타낸 문자열 나타냄    ex) / by zero

 
1
2
3
4
5
6
7
8
9
10
11
12
try {
 
    System.out.println(5 / 0);
 
catch (Exception e) {
 
    e.printStackTrace(); 
 
    String msg = e.getMessage(); //java.lang.ArithmeticException: / by zero
 
    System.out.println("Exception: " + msg); //Exception: / by zero 
}
cs


결과:



2. throws 키워드 사용하여 메소드에 예외 선언하기

:예외처리 직접 하지 않고 호출한 곳으로 넘김 (단순히 예외를 전달만 하므로 결국 try-catch문으로 예외처리 필요) 



사용자 정의 예외 클래스

자바에서는 Exception 클래스를 상속받아 자신만의 새로운 예외 클래스를 정의하여 사용 가능 

사용자 정의 예외 클래스에는 생성자뿐만 아니라 필드 및 메소드도 원하는 만큼 추가 가능


(요즘에는 Exception 클래스가 아닌 예외 처리를 강제하지 않는 RuntimeException 클래스를 상속받아 작성하는 경우 많음)

1
2
3
4
5
6
7
class MyException extends RuntimeException {
 
    MyException(String errMsg) {
 
        super(errMsg);
    }
}
cs



try-with-resources 문 (자동 자원 반환)

JDK1.7부터 try-with resources문이라는 try-catch문의 변형이 새로 추가됨 
-이 구문은 주로 입출력(I/O)과 관련된 클래스 사용 때 유용

ex) 파일에서 문자열을 한 줄 읽어오는 예제
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
static String readFile(String filePath) throws IOException {
 
    BufferedReader br = new BufferedReader(new FileReader(filePath));
 
    try {
 
        return br.readLine();
 
    } finally {
 
        if (br != null)
 
            br.close();
    }
}
cs

위와 같이 Java SE 7 이전에서는 finally 블록을 사용하여 사용한 파일을 닫아줘야 했음 


하지만 try-with-resources 문을 사용하면 다음과 같이 자동으로 파일의 닫기를 수행할 수 있음

1
2
3
4
5
6
7
static String readFile(String filePath) throws IOException {
 
    try (BufferedReader br = new BufferedReader(new FileReader(filePath))) {
 
        return br.readLine();
    }
}
cs




제어자란?

-주로 클래스, 변수 또는 메소드에 사용되며, 부가적 의미를 부여

-크게 접근제어자와 기타제어자로 나눌 수 있음

 

접근제어자(4가지 중 하나만 선택해서 사용 가능) public, protected, default, private 

기타제어자(여러 제어자 조합하여 사용 가능)  :     static, fianl, abstractm native, transient, synchronized, volatile, strictfp

 

 

Ⅰ.접근제어자

접근 제어자를 사용하는 이유

 

 - 데이터가 유효한 값을 유지하도록, 또는 비밀번호와 같은 데이털르 외부에서 함부로 변경하지 못하도록 하기 위해 .

  이것을 데이터 감추기 또는 데이터 은닉(data hiding)이라고 하며, 객체지향개념의 캡슐화(encapsulation)에 해당

  -외부에서 접근할 필요가 없는 멤버들을 private으로 지정하여 외부에 노출시키지 않음으로써 복잡성 줄임.

 

 

 

접근범위가 넓은 쪽에서 좁은 쪽의 순으로 왼쪽부터 나열

public > protected > (default) > private  

 

제어자 

같은 클래스 

같은 패키지  

다른 패키지 자손클래스 

전체 

public 

 

 

 

 

protected

 

 

 

 

(default) 

 

 

 

 

 private

 

 

 

 

 

 

 

private 접근제어자:

private 접근 제어자를 사용하여 선언된 클래스 멤버는 외부에 공개되지 않으며, 외부에서는 직접 접근 X

즉, 자바 프로그램은 private 멤버에 직접 접근할 수 없으며, 해당 객체의 public 메소드를 통해서만 접근할 수 O

private

 

 

 

default 접근제어자:

default를 위한 접근 제어자는 따로 존재 안하며, 접근 제어자가 지정되지 않으면 자동적으로 default 접근 제어를 갖게됨

 

 

default 접근 제어를 가지는 멤버는 같은 클래스의 멤버와 같은 패키지에 속하는 멤버에서만 접근할 수 있음.

default

 

 

 

 

 

protected 접근제어자:

-같은 패키지 내에서, 그리고 다른 패키지의 자식클래스에서 접근 가능

 protected

 

 

 

public 접근제어자:

public 접근 제어자를 사용하여 선언된 클래스 멤버는 외부로 공개되며, 해당 객체를 사용하는 프로그램 어디에서나 직접 접근 가능

 default

 

 

 

 

Ⅱ.기타제어자

-static, fianl, abstractm native, transient, synchronized, volatile, strictfp

-하나의 대상에 대해 여러 제어자를 조합하여 사용하는 것이 가능

 

static - 클래스의, 공통적인

 사용될 수 있는 곳 - 클래스, 메소드, 초기화 블럭

 

<static이 붙은 멤버변수>

-모든 인스턴스에 공통적으로 사용되는 클래스변수(=static이 붙은 변수)가 됨

-클래스변수는 인스턴스 생성하지 않고도 사용 가능

-클래스가 메모리에 로드될 때 생성됨 

 

<static이 붙은 메소드>

-인스턴스를 생성하지 않고도 사용 가능

-static이 붙은 메소드 내에서는 인스턴스 멤버들을 직접 사용할 수 X

 

 

 

final - 마지막의, 변경될 수 없는

-마지막, 또는 변경될 수 없는 의미를 가지며 거의 모든 대상에 사용 가능

 

용될 수 있는 곳 - 클래스, 메소드, 멤버변수, 지역변수  

 

-final이 붙은 변수는 상수이므로 일반적으로 선언과 초기화를 동시에 하지만, 생성자를 이용하여 인스터스변수의 경우 final멤버변수의 초기화를 가능하게 함

즉, 클래스 내에 매개변수를 갖는 생성자를 선언하여 final이 붙은 멤버변수가 다른 값을 갖도록 하는 것이 가능

 

 

 

abstract - 추상의, 미완성의

-'미완성'의 의미를 가지므로 메소드의 선언부만 작성하고 실제 수행내용은 구현하지 않은 추상메소드 선언 시 사용 됨

 용될 수 있는 곳 - 클래스, 메소드

 

 

다형성이란? 


-여러 가지 형태를 가질 수 있는 능력으로, 자바에서는 한 타입의 참조변수로 여러 타입의 객체를 참조할 수 있도록 함 


무슨 말이냐?? 조상클래스 타입의 참조변수로 자손클래스의 인스턴스를 참조할 수 있도록 하였다는 것 

(※참고:  조상클래스 = 부모클래스, 자손클래스 = 자식클래스)


아래 예시를 보며 자바에서의 '다형성' 의미를 알아봅시다. 




예시) 

왼쪽 사진) TV클래스 (부모클래스)

오른쪽 사진) TV클래스를 상속받고 있는 CaptionTV 클래스 (자식클래스) 


 

생성된 TV클래스와 CaptionTV 클래스를 다루기 위해, 일반적으로 인스턴스의 타입과 일치하는 타입의 참조변수를 사용하면 아래와 같습니다. 

TV t = new TV();                          //TV클래스에서만 선언된 변수 및 메소드 호출가능

CaptionTV c = new CaptionTV();    //TV클래스를 상속받아서, TV클래스 & CaptionTV클래스에 선언된 변수 및 메소드 호출가능



하지만 두 클래스가 서로 상속관계에 있을 경우, 다음과 같이 부모 클래스 타입의 참조변수로 자손 클래스의 인스턴스를 참조하도록 하는 것도 가능! 

 

TV t = new CaptionTV();    




그렇다면 인스턴스를 같은 타입의 참조변수로 참조하는 것과 부모타입의 참조변수로 참조하는 것은 어떤 차이가 있나?


: 둘 다 같은 타입의 인스턴스(ex. CaptionTV())지만 참조변수의 타입(ex. c와 t)에 따라 사용할 수 있는 멤버의 개수가 달라짐

부모클래스 타입의 참조변수 t로는 CaptionTV 인스턴스의 모든 멤버 사용 X 


CaptionTV c = new CaptionTV(); 


c.power;

c.channel;

c.power();

c.channelUp();

c.channelDown(); 

c.text;

c.caption(); 



    TV t = new CaptionTV(); 



t.power;

t.channel;

t.power();

t.channelUp();

t.channelDown(); 

t.text;                     //사용불가

t.caption();              //사용불가



 


참고로 

자식타입의 참조변수로 부모타입의 인서턴스 참조는 불가능함. 왜냐하면 실제 인스턴스인 TV의 멤버개수보다 자식클래스에서 사용할 수 있는 멤버 개수가 더 많기 때문에 이를 허용하지 않음 

ex)

1
2
3
4
5
6
7
8
9
10
11
12
13
class Parent { ... }
 
class Child extends Parent { ... }
 
...
 
Parent p = new Parent(); // 허용
 
Child c = new Child();   // 허용
 
Parent pc = new Child();  // 허용
 
Child cp = new Parent();  // 오류 발생



정리하면, 부모타입의 참조변수로 자식타입의 인스턴스를 참조할 수 있다.

하지만 자식타입의 참조변수로 조상타입의 인스턴스는 참조할 수 X 



다형성) 참조변수와 인스턴스의 연결 

-부모 클래스에 선언된 멤버변수와 같은 이름의 인스턴스변수를 자식 클래스에 중복했을 때, 

참조변수의 타입에 따라 서로 다른 결과를 얻음


Child cp = new Child();Parent pc = new Child();서로 다른 결과를 얻음 


메서드의 경우, 부모 클래스의 메소드를 자식클래스에서 오버라이딩한 경우에도 참조변수 타입과 관계없이 오버라이딩된 메소드가 호출되지만, 멤버변수의 경우조변수의 타입에 따라 달라짐


-그렇다면 멤버변수가 어떻게 달라지나?

    -부모클래스타입의 참조변수를 사용했을 때는 (ex. Parent p = new Child(); ) 부모클래스에 선언된 멤버변수가 사용됨

    -자식클래스타입의 참조변수를 사용했을 때는 (ex. Child c = new Child(); ) 자식클래스에 선언된 멤버변수가 사용됨 


 ex)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
public class MainClass {
 
    public static void main(String[] args) {
        Parent p = new Child();  //부모클래스타입의 참조변수를 사용
        Child c = new Child();   //자식클래스타입의 참조변수를 사용
        
        System.out.println("p.x = " + p.x);  //멤버변수 호출
        p.method();                          //메소드 호출
        System.out.println("c.x =" + c.x);   //멤버변수 호출
        c.method();                          //메소드 호출
        
    }
    
    class Parent {
        int x = 100;
        void method() {
            System.out.println("Parent method");
        }
    }
    
    class Child extends Parent {
        int x = 200;
        void method() {
            System.out.println("Child method");
        }
    }
}
 
cs


결과

 p.x = 100

Child Method

c.x = 200

Child Method





다형성) 참조변수의 형변환


-서로 상속관계에 있는 타입간의 형변환은 양방향으로 자유롭게 수행 가능!! 

-그러나 기본형 변수의 형변환에서 작은 자료형에서 큰 자료형의 형변환은 생략 가능하듯, 참조형 변수의 형변환에서는

자식타입의 참조변수를 부모타입으로 형변환하는 경우에 명식적인 형변환 생략 가능 


● 자식타입 → 조상타입 (Up-casting) :      형변환 생략가능

● 조상타입 → 자식타입 (Down-casting) :  형변환 생략불가 

       -문법: (변환할타입의클래스이름) 변환할참조변수


ex)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
class Parent { ... }
 
class Child extends Parent { ... }
 
class Brother extends Parent { ... }
 
...
 
Parent pa01 = null;
 
Child ch = new Child();
 
Parent pa02 = new Parent();
 
Brother br = null;
 
 
 
pa01 = ch;          // pa01 = (Parent)ch; 와 같으며, 타입 변환을 생략할 수 있음.
 
br = (Brother)pa02; // 타입 변환을 생략 
 
br = (Brother)ch;   // 직접적인 상속 관계가 아니므로, 오류 발생.
cs





다형성) instanceof 연산자

이러한 다형성으로 인해 런타임에 참조 변수가 실제로 참조하고 있는 인스턴스의 타입을 확인할 필요성 생김

자바에서는 instanceof 연산자를 제공하여, 참조 변수가 참조하고 있는 인스턴스의 실제 타입을 확인할 수 있도록 함 

자바에서 instanceof 연산자는 다음과 같이 사용함


문법:  참조변수 instanceof 클래스이름 


-주로 조건문에 사용되며 instanceof의 왼쪽에는 참조변수, 오른쪽에는 타입(클래스명)이 피연산자로 위치

-그리고 연산의 결과로 boolean값이 true와 false 중의 하나를 반환 

(true를 얻었다는 것은 참조변수가 검사한 타입으로 형변환이 가능하다는 것을 뜻함


ex)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
class Parent { }
 
class Child extends Parent { }
 
class Brother extends Parent { }
 
 
 
public class Polymorphism01 {
 
    public static void main(String[] args) {
 
        Parent p = new Parent();
 
        System.out.println(p instanceof Object); // true
 
        System.out.println(p instanceof Parent); // true
 
        System.out.println(p instanceof Child);  // false
 
        System.out.println();
 
 
 
        Parent c = new Child();
 
        System.out.println(c instanceof Object); // true
 
        System.out.println(c instanceof Parent); // true
 
        System.out.println(c instanceof Child);  // true
 
    }
 
}
cs






+ Recent posts