날아라쩡글이의 블로그입니다.
I/O(Data, Object)와 직렬화 본문
728x90
반응형
Stream이란 읽거나 보내는 것을 의미한다.
- int read(byte[] buf)
- 미리 byte[]객체를 만들고, 읽어온 데이터를 순서대로 저장,
- byte[]에 저장된 값이 124KB일 경 반환값은 int값으로 지정, int값은 배열에 저장된 값으로 int로 저장된다.
- BufferedInputStream
- 읽기기능을 성능을 향상시킨다.
- DataInputStream
- DataOutputStream 출력데이터를 읽어옴
- DataIntputStream은 출력데이터가 읽을 입력데이터를 작성한다.
- 타입의 값 그대로 출력시킨 값을 읽어서 원래 값으로 복원시키는 스트림
- 값의 자료형도 같이 내보냄(값 + 데이터타입)
- writeInt() ->readInt() 그 값의 그대로 보관
- writeUTF()->readUTF() 값을 전달시 글자 그대로 저장됨
- 그렇기 때문에 순서가 중요하다, 입력된 Int, UTF순서대로 불러와야한다.
- 안그러면 완전히 다른값이 출력된다.
- App-> App의 파일을 주고 받은 경우 File 이름, 크기 , 그자체 (String,Long, Byte[])->한꺼번에 전달시사용한다
- writeUTF() 파일제목
- 읽어올 때 readUTF()
- writeLong() 파일크기
- readLong()
- writeInt,Byte() 파일
- readInt,Byte()
- DataOutputStream 출력데이터를 읽어옴
ObjectInputStream
- 객체자체를 읽고, 쓰고 싶을 때, 사용한다.
- 왜 객체를 내보내는 것일까?
- 클라이언트측에서는 요청을 서버로 보낸다. 아주 많은 양의 서버를 보낸다.
- 로드밸런스에서는 서버로 각기 보내주는데, 여러가지의 서버에서 보내고 있다.
- 그럼A라는 클라이언트에서는 로그인요청을 하고,서버1에서 로그인을 하고, 다른 요청시 서버3에 가게되면 객체에 대한 정보가 없고, 서버가 다르기 때문에 로그아웃이 된다. 그렇다면? 너무 불편할 것이다.
- 이것의 해결방법은 어딜가나 로그인상태로 유지시키는 것이다.
- 서버1에서 서버 3으로 객체를 복사하여 보내는 것을 다중화라고 한다.
- 어떤 서버에 Output으로 보내고, 다른 서버에 Input으로 저장되는 것을 직렬화, 역직렬화라고 한다.
- 객체를 구현할 일은 없다. 우리 사용서버에 클러스트링이 구현하고 있다.
- ObjectOutput
- ObjectInput으로 역/ 직렬화 작업을 하고 있다.
ByteArrayInput
- byte 배열을 만들면 메모리에 있는 것을 읽어온다.
- 배열의 값을 담는 순간 객체로 만들어져 메모리에 있는 것을 읽어온다.
PipedInputStream
- 멀티스레드 환경을 사용한다.
OutputStream 클래스의 메소드
- void write(int byte)
- 4byte지만 data는 1byte를 갖고 있는 int객체를 내보낸다.
- void write(byte[] buf) 1byte의 data를 byte배열에 저장한다.
- flush()
- Buffered는 내부저장소를 가지고 있다. 8KB씩내보내는데,
- 가득찼을때만 내보낸다. 그렇기 때문에 마지막에는 데이터가 남아있을 수 있다.
- 내보내지 않을 수 있는데, close를 사용하면 내보내고 닫아버린다.
- 닫지 않고 내보내게 만드는 것이 flush()이다.
- 카카오톡의 경우 8KB를 전체로 보내지 않고 중간중간 보내는 것을 알 수 있다.
- 8KB는 8196byte이다. 전송을 중간중간 보내는 방법은?
- close를 하면 카카오톡이 그냥 종료를 해버릴 것이다.
- 연결 유지를 원하면서 보내고 싶을 때 flush를 사용한다.
- Stream의 내부저장소를 유지하면서 자료를 보낸다
- Output에서만 존재한다.
- BufferedOutputStream에서 flush()꼭 호출한다.
출력전용의 PrintStream
- BufferedReader 만 사용한다.
- 한 줄씩 얻는 readLine() 메소드를 사용하기 때문이다.
- BufferedReader reader = new BufferedReader(new InputStreamReader(System.in))
- 키보드입력을 읽어오는 System.in을 연결하여, 장치로 읽어 올 수 있다.
- BufferedReader reader = new BufferedReader(new InputStreamReader(new FileInputStream))
- 브릿지 new InputStreamReader을 이용하여 new FileInputStream을 읽어올 수 있다.
Socket이란
- 데이터, 네트워크 전송시 자신과 연결된 반대편 Socket에게 데이터를 전달해주는 것이다.
- 네트워크 통신에서 다른 네트워크 통신으로 연결하는 것은 파일기록하는 것과 동일하다.
- 컴퓨터의 파일을 기록 PrintWrite로 입력하고 write.println()으로 내보낸다.
- 다른 파일은 BufferedReader로 읽어들이고 nextLine()으로 읽어들인다.
- A네트워크가 OutputStream 이라면
- B네트워크에서는 InputStream으로 진행이된다.
ObejctOutputStream
- 객체를 직렬화 시키고 출력하는 스트림이다.
- 직렬화는 객체를 스트림으로 출력가능한 상태로 변환하는 것을 말한다.
- 직렬화는 생성된 객체의 클래스명, 멤버변수의 이름과 타입, 멤버변수에 저장된 값을 Stream으로 출력하는 것이다.
- 네트워크 전송도 당연히 가능하다.
- 매개변수 모두 직렬화를 해줘야한다.
- 한개라도 직렬화가 포함되어 있지 않다면 직렬화가 되지 않는다.
- Data,String은 자동으로 직렬화가 되어있다.
- 직렬화를 하기 위해서는 직렬화 마크업 인터페이스를 입력해야 직렬화가 가능하다.
- 역직렬화에서 제외하기
- transient키워드를 사용하면 직렬화에서 제외된다.
- private transient String password; //역직렬화에서 제외되는 키워드(VO에서 입력해주어야한다.)
- 생성된 객체를 직렬화하고, Stream으로 출력하는 것은, 복제를 허락해야 가능하다.
- implements Serializable
- 직렬화하려는 VO에 마크업 인터페이스를 구현해야한다.
ObjectInputStrema
- 직렬된 객체를 읽어서 역직렬화 하는 스트림이다.
- 역직렬화는 직렬화된 객체 정보를 읽어서 객체를 저장하고, 멤버변수 값도 복원하는 것이다.
- readObject의 반환타입의 경우 어떤 객체가 올지 지정할 수 없어 최고조상이 Object로 반환타입을 입력해주어야한다.
private static final long serialVersionUID = 2034123329551617274L;
- 역직렬화를 위해서라면 똑같은 위치에 똑같은 class가 있어야지 된다.
- User.java를 컴파일하게 된다면 User.class가 완성되는데 거기에는 serialVersionUID이라는 시리얼 번호가 추가된다.
- java.io.serializable : 인터페이스를 구현한 소스파일을 컴파일하면 실행파일에 자동으로 추가된 값이다.
- Stream을 이용해서 객체를 직렬화/ 역직렬화 할때 객체나 클래스를 식별하는 값으로 사용된다.
- 컴파일할때마다 시리얼 UID가 변경된다(고정된 값이 아니기 때문)
- 같은 파일인지 확인 할때 클래스명.text로 비교시 오래 걸린다.
- 짧게 확인하기 위하여 UID 끼리 비교하게 넣은 시리얼 번호다.
- But컴파일시마다 변경되기 때문에 private static final로 고정시켜놓은 것이다.
반응형
'중앙 HTA (2106기) story > java API story' 카테고리의 다른 글
Optional (0) | 2022.01.04 |
---|---|
Stream메소드 사용법 (자바 8버젼이상) (0) | 2022.01.03 |
I/O (0) | 2021.10.14 |
사용자 정의 예외 처리 , 앞으로 코딩 작성 방법(맨 밑) (0) | 2021.10.13 |
Formating (포맷팅) (0) | 2021.10.08 |
Comments