객체지향 프로그래밍과 설계(1)
업데이트:
POCU의 개체지향 프로그래밍 및 설계 강의를 듣고 정리한 내용입니다.
메인 함수
최고 레벨의 public
클래스는 하나만!
- 한
.java
파일에는 최고 레벨 public 클래스가 하나만 있어야 함. - 둘 이상일 경우 컴파일 에러
클래스 안에 다른 클래스를 넣을 수 있음 (nested class)
- public이어도 상관 없음
main
함수
public static void main(String[] args) {
...
}
- 프로그램의 entry point
- 반드시 signature대로 만들어야 함
- 그렇지 않으면 런타임 에러
String[] args
- 문자열 배열
- 커맨드 라인으로부터 받은 인자
출력문과 가변 인자
System.out.println("Hello POCU");
- System : 클래스
- out : System 클래스의 static 멤버 변수
- out의 자료형은
PrintStream
클래스 - 즉, out은 object
- printStream은 자바의 표준 출력 스트림
- out의 자료형은
println()
은 문자열, 숫자, 문자 등을 출력 가능
- 함수 오버로딩이 적용되어 있다.
java에도 printf()
가 있다
System.out.printf("%s's score : %d\n", "Chan", 19)
format()
메서드를 사용해도 동일하게 동작- 문자열 포맷팅 가능
올바른 개행문자 추가 방법
public static String lineSeparator();
System.out.printf("%s's score :%d%s", "chan", 19, System.lineSeparator());
- 플랫폼에 맞는 개행문자를 반환하는 메서드
- linux :
\n
- windows :
\r\n
- linux :
가변 인자
public PrintStream printf(Stirng format, Object... args);
// <자료형>... <매개변수 이름>
public void printNames(String... name) {...} // String 타입만 전달
public void printScores(int... score) {...}
패키지
package <패키지 경로>;
- 연관된 클래스들끼리 묶는 기법(namespace)
종류
- built-in 패키지
- 이름이 java로 시작하는 패키지들
- 프로그래머가 만든 패키지
목적
- 이름 충돌 문제를 피할 수 있게 해 줌
패키지 이름 짓기
- 중복을 최소화해야 함
- 보통 회사의 도메인명을 패키지 이름에 사용(역순으로)
package acadamy.pocu.<패키지 이름>;
패키지명과 똑같은 폴더 트리에 .java 파일을 넣어야 함
pjt/src/academy/pocu/Hello.java
- src : 모든 .java 파일이 들어가는 폴더
빌드 및 실행
pjt - src - academy - pocu - Hello.java
ㄴ- class - academy - pocu - Hello.class
javac : 자바 컴파일러
javac -d <컴파일 결과를 저장할 경로> <컴파일할 .java 파일>
- .class : 바이트 코드가 들어 있음
- 기계어 아님. 특별한 명령어
-d
: .class 파일을 저장할 경로
java 명령어
java -classpath <class 파일 위치> <클래스 이름>
- .class의 바이트 코드를 실행하는 명령어
<클래스 이름>
- 실행할 .class파일 이름
- 반드시 main함수 있어야 함
클래스 이름 앞에 반드시 패키지 이름을 붙여야 함
배포하기
라이브러리, 프로그램 모두 .jar
파일을 만듬
pjt - src - ...
ㄴ- class - ...
ㄴ- lib - <jar파일>
jar명령어
jar <option> <jar 파일 이름> <최상위 패키지 경로>
- .jar 파일을 생성한다.
-cf
- c : 생성
- f : jar파일의 이름을 지정
Manifest 파일
- 자바 애플리케이션의 정보를 담고 있는 메타데이터 파일
- .jar 파일을 만들 때 같이 넣어줄 수 있음
- .jar 파일의 시작점(메인 함수)에 대한 정보를 넣어야 함
pjt - src - academy
| ㄴ- Manifest.txt
ㄴ - class - ...
- lib - <jar파일>
// Manifest.txt
Main-Class:academy.pocu.HelloPocu
...
패키지 사용하기
import java.util.Randon;
- java.util 패키지의 Random 클래스를 import
java.lang
- 기본 패키지
- 모든 .java 파일에 자동으로 임포트되는 패키지
import java.lang.*;
- System은 java.lang 안에 있는 클래스 중 하나
자바의 실행 모델
코드를 컴파일 한 결과는 바이트 코드
- 실행 파일이 아님
- JVM이라는 특수한 프로그램이 이해하는 명령어
- JVM이 실행 중에 최종 플랫폼에 맞는 명령어로 바꿔서 실행해줌
- JVM에 맞게 최적화 됐지만 당연히 기계어보다는 느림
JVM
OS에 설치하는 별도의 프로그램
- OS/디바이스마다 다른 버전을 설치
- OS나 디바이스의 영향을 받지 않음
실행하는 방식
- 과거에는 인터프리터 방식
- 최신은 just-in-time 컴파일 방식
- 여러 방식이 공존하는 형태
char, boolean, String
Char
16비트 정수형 U+FFFF 이상은 String 사용해야 함.
기본 자료형은 모두 value type
String
- 연속된 문자를 표현하는 클래스형
- 클래스는 언제나 참조형
- String 클래스의 구성
- 연속된 문자를 저장하는 메모리
- 위 데이터를 처리할 수 있는 각종 메서드
- 클래스형이므로
new
를 이용해서 개체 생성도 가능
자바의 String은 immutable
- 컴파일 에러 난다.
리터럴
- int의 리터럴 : 없음
- long의 리터럴 : L 혹은 l
- 생략 가능
- int의 범위보다 큰 수일 때 생략하면 컴파일 오류
long num4 = 123456734545890 // 컴파일 에러
- float : F or f
-
double : D or d. 보통 생략
- 문자 : 작은 따옴표
- 문자열 : 큰 따옴표
- 유니코드 :
\uNNNN
null
- 참조형에 사용 가능한 리터럴
- 의미 : 참조하는 대상이 없음(Null pointer)
_
- 큰 숫자의 가독성을 높이기 위해 사용
- Java 7부터
Final 키워드
자바의 상수형 변수
final int MAX_STUDENT = 10;
MAX_STUDENT = 30; // 컴파일 에러
final
키워드를 붙일 수 있는 곳
- 지역 변수
- 클래스 멤버 변수
- 메서드 매개변수
- 클래스와 메서드
final 변수의 초기화
public class StudentManager {
public final int MAX_STUDENT = 10;
public void printScores() {
final int MAX_CLASS = 5;
...
}
...
}
- 선언과 동시에
- 사용하기 전에만
- 지역 변수일 경우 실제로 final 변수를 사용하기 전에만 초기화해주면 됨.
- 멤버 변수일 경우 생성자에서 초기화 가능.
- 그 외의 메서드에서 초기화 할 경우 컴파일 오류 발생
주석 / 산술 연산자
Javadoc
/**
* Returns the greater of two int values
* @param num1 an argument
* @param num2 another argument
* @return the larger of num1 and num2
*/
public int max(int num1, int num2){
return num1 > num2 ? num1 : num2;
}
- 클래스, 메서드, 멤버변수, 인터페이스 위에 위치
- 자동으로 Java API 문서 생성
산술 연산자
- 기본적으로 숫자를 표현하는 자료형만 피연산자로 사용 가능
- 예외 : 문자열 더하기
- 불리언형에 사용 불가
- 문자형(char)은 가능
- 자바에서 char는 정수
대입 연산자
- value type일 경우 값을 복사
- reference type일 경우 주소를 복사 (swallow copy)
String 도 클래스니 reference type
- 대입 연산자는 value를 바꾸지 않는다.
- 대신 우항의 String을 reference
문자열 비교
String name1 = "Nana";
String name2 = "Nana";
String name3 = new String(name1);
String name1 = new String("Nana");
boolean isSame1 = (name1 == name2) // true
boolean isSame2 = (name1 == name3) // false
boolean isSame3 = (name1 == name4) // false
boolean isSame3 = (name1 == "Nana") // true
문자열은 reference type
- 문자열 변수에 저장되어 있는 건 값이 아니라 메모리 주소
- 따라서
==
가 비교하는 대상은- 주소
- 주소의 실제 문자열이 아님
주소를 공유하는 경우
- String을
new
로 생성하지 않은 경우- String constant pool / String pool 참고
문자열 자체를 비교하려면
equals()
메서드
비트 연산자
>>>
연산자
- Unsigned 비트 연산자
- 오른쪽으로 이동 후 남는 공간을
0
으로 채움 - Java에는 unsigned 자료형이 없기에 이렇게 연산자를 따로 만듦
반복문
goto
- java에서는
goto
지원 안 함.
사용하면 좋은 경우
- 다른 언어에서 중첩된 반복문 탈출하는 코드를 짜야 할 때 유용하다.
break <라벨이름>
loop_exit:
for (int i = 0; i < DEPTH; ++i){
for (int j = 0; j <HEIGHT; ++j){
for (int k = 0; k < WIDTH; ++k){
if (data[i][j][k] == 1){
System.out.println(date[i][j][k]);
} else {
break loop_exit;
}
}
}
}
break
를 감싸고 있는 라벨로만 점프 가능continue
역시 라벨을 사용할 수 있다.
foreacch
스타일의 for문
int[] scores = {10, 20, 30, 40};
for (int score : scores){
System.out.printf("%d", score);
}
- 어떤 컬렉션이든 순회할 수 있는 반복문
final
참조형 매개변수
- 참조형 변수는 주소를 저장
- 따라서
final
이 붙으면 그 주소만 변경 못 함 - 그 주소가 가리키는 값(멤버 값)은 여전히 바꿀 수 있음
public static Vector add(final Vector v1, final Vector v2) { ... v1.x += 6547.0f; // OK v1 = new Vector(20, 30) // Compile Error! ... }
배열
1차원 배열
<자료형>[] <변수명> = new <자료형>[<크기>];
다차원 배열
<자료형>[][][] <변수명> = new <자료형>[<크기>][<크기>][<크기>];
- 진짜 다차원 배열이 아님
- 배열의 배열
- 안쪽 배열의 길이가 다를 수 있음
var
- java 10부터 지원
- 컴파일러가 알아서 자료형 추론
- 선언과 동시에 값을 대입해야 함
- 배열 선언 시 변수 이름에
[]
사용할 수 없음 - 선언과 동시에
{}
를 이용해 값을 대입할 수 없음
var num = 10;
var message = "zz";
var error; // Compile err
var numbers[] = nuw int[20]; //Compile err
var world = new int[100][200][300] ; // OK
var names = {"A", "B", "C"} //Compile err
람다
() -> System.out.println("Hi");
(name) -> System.out.println("Hi"+name);
- 무명 함수로 nested 함수라고도 부름
모듈
- 패키지의 상위 개념
- 모듈 간의 의존성 관리가 쉽다.
- 꼭 필요한 패키지만 메모리에 할당할 수 있다.
module-info.java
파일로 모듈 관리
댓글남기기