1) 입출력 스트림
2)파일입출력스트림
3)보조스트림(BufferedStream)
4)ObjectStream
5)SequenceStream
6)쓰레드
6-1)쓰레드의 동기화
6-2)Daemon 쓰레드
6-3) 쓰레드 정리
7) Function패키지 ( 람다)
1) @ 입출력 스트림 @
출력스트림 : 외부로데이터전송
입력스트림 : 외부데이터 읽기
입출력스트림의 예시를 하나씩만해보자!
입력스트림
InputStream은 바이트형(1byte)입력
InputStreamReader : 문자형(1char)입력
public class InputStreamEx2 {
public static void main(String[] args) throws IOException {
InputStream is = System.in;
int data=0;
while((data=is.read())!= -1) {
System.out.print((char)data+"");
}
}
}
/*
ggg
ggg
안녕하세요
ìë
íì¸ì //InputStream 은 1byte단위로 읽어오므로 문자열이깨짐
*/
/*
InputStreamReader is = new InputStreamReader(System.in);
로 변경 시
ㅋㅋㅋ
ㅋㅋㅋ
안녕하세요
안녕하세요
*/
출력스트림
public class Ex {
public static void main(String[] args) throws IOException {
OutputStream os = System.out;
os.write('1');os.write('2');os.write('3');
os.write('g');os.write('d');os.write('s');
os.write('가');os.write('니');os.write('다');
os.flush();
os.close();
}
}
한글같은경우는 1byte로표현이되지않기에 깨지게 됨
public class Ex {
public static void main(String[] args) throws IOException {
// OutputStream os = System.out;
OutputStreamWriter os = new OutputStreamWriter(System.out);
os.write('1');os.write('2');os.write('3');
os.write('g');os.write('d');os.write('s');
os.write('가');os.write('니');os.write('다');
os.flush();
os.close();
}
}
123gds가니다
Writer로 변경시 문자형으로 출력함
2) @@ 파일입출력스트림 @@
public class MyEx {
public static void main(String[] args) throws IOException {
FileInputStream fi = new FileInputStream("src\\ex2_outputStream\\Exam1_Writer.java");
FileOutputStream fo = new FileOutputStream("my2.txt");
byte[] b = new byte[fi.available()];//fi의 읽기가능한 수
int data2=0;
while((data2=fi.read(b))!=-1) {
fo.write(b);
}
fi.close();
fo.flush();
fo.close();
Reader r = new FileReader("src/ex2_outputStream/Ex.java");
FileWriter fw = new FileWriter("my.txt");
char[] c = new char[8000];
int data=0;
while((data=r.read(c,0,c.length))!= -1) {
//c의 0 번인덱스부터 c의 크기까지 읽어라(실제크기리턴)
fw.write(c);//c(char)을 그대로 write
}
fw.flush();
//항상 스트림은 닫아주기
r.close();
fw.close();
}
}
용어들은 모두 같다 (앞에 file이 붙은 게 끝)
FileInputStream :
read() : 1byte단위로 읽어옴
read(byte[] buf) 파일에서 buf크기만큼 읽어 buf에 내용을 저장 후 읽은 수 리턴
FileReader :
read() : 1char단위로 읽음
read(char[] c) 파일에서c크기만큼읽어 c에 내용 저장 후 읽은 수를 리턴
FileoutputStream :
write(int data) : 1byte단위로 출력
write(byte[] buf) : buf의 내용 출력
FileWriter ::
write(int data) : 1char단위로 출력
write(char[] buf) : buf의 내용 출력
write(String str) : str문자열의 내용을 출력
3) @@ 보조스트림 @@
BufferedReader
보조스트림이란?
* 1. 기존의 스트림에 새로운기능을 추가
* 2. 객체 생성시 다른 스트림을 생성자의 매개변수로받는다
BufferedReader는 한줄씩 읽어온다는 장점이 있음!!!!
public class BufferedReaderEx1 {
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
//br : 키보드에서입력된내용을 한줄씩 읽을수있음(readLine())
System.out.println("저장할 내용을 입력 ( 종료 : ctrl+Z )");
Writer w = new FileWriter("bufferd.txt");
String data=null;
while((data=br.readLine())!= null) {
System.out.println(data);
w.write(data+"\n");
}
w.flush();w.close();
br.close();
}
}
저장할 내용을 입력 ( 종료 : ctrl+Z )
하이
하이
루
루
하이루
하이루
4)@@ ObjectStream @@
ObjectOutputStream
* 1. 객체를 외부로전송 할 수 있는 스트림
* 2. 외부전송이 가능한 객체는 반드시 Serializable 인터페이스를 구현해야함
* ==> 직렬화
* ==> Serializable 인터페이스를 구현하지않은 객체를 외부전송시
* NotSerializableException발생
* 3.ObjectOutputStream으로 전송된객체는 ObjectInputStream객체로읽음
class Customer implements Serializable{//꼭 구현!
private String name;
private int age;
//transient : 직렬화 대상의 객체에서 해당멤버는 제외
private transient int pw;
public Customer(String name, int age,int pw) {
super();
this.name = name;
this.age = age;
this.pw = pw;
}
@Override
public String toString() {
return name +","+ age +","+pw ;
}
}
//-------------------------------------------------------------------------------------------
public class ObjectOutputSteamEx1 {
public static void main(String[] args) throws IOException {
//fos스트림의 목적지 : object.ser
FileOutputStream fos = new FileOutputStream("object.ser");
ObjectOutputStream oos = new ObjectOutputStream(fos/*목적지*/);
Customer c1 = new Customer("하이", 44,9844);
Customer c2 = new Customer("루", 24,5312);
System.out.println(c1);
System.out.println(c2);
oos.writeObject(c1);//c1객체를 object.ser로 전송
oos.writeObject(c2);//c2객체를 object.ser로 전송
oos.close();
fos.close();
}
}
다음과같이 객체 자체를전송이 가능함.
ObjectInputStream(new FileInputStream())으로 읽어오기
public class ObjectInputStreamEx1 {
public static void main(String[] args) throws IOException, ClassNotFoundException {
//ois스트림 : object.ser파일에서 객체를 읽을 수 있는 스트림
ObjectInputStream ois = new ObjectInputStream(new FileInputStream("object.ser"));
int data=0;
Customer c1 = (Customer) ois.readObject();//object->Customer로 다운캐스팅
Customer c2 = (Customer) ois.readObject();//readObject() 메서드의 리턴타입 : Object
// Object c1 = ois.readObject();
// Object c2 = ois.readObject(); 출력은 다운캐스팅을 하나 안하나 똑같음
System.out.println(c1);
System.out.println(c2);
}
}
유동곤,1233,24
김삿갓,643,16
5) Sequence Stream
여러개의 스트림을 하나의스트림으로 합침
package ex7_other;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.SequenceInputStream;
import java.util.Vector;
public class SequenceStreamEx1 {
public static void main(String[] args) throws IOException {
File f = new File("src/sequen");
String[] files = f.list();
//꼭 Vector를 사용하자 (ArrayList등을 사용하면 v.elements사용불가)
//Vector는 Enumeration을 제공
Vector<InputStream> v = new Vector<InputStream>();
for(String file : files) {
File f2 = new File(f,file);
if(f2.isFile()) {
v.add(new FileInputStream(f2));//f2파일을 vector에 저장
}
}
//Enumeration v.elements();
//s :[new FileInputStream("Exam1.java),("FileEx1.java)..... 등
// 여러개의 스트림을 한개의 스트림으로 연결시켜줌
SequenceInputStream s = new SequenceInputStream(v.elements());
FileOutputStream fos = new FileOutputStream("file예제2.txt");
int data = 0;
byte[] buf = new byte[s.available()];//s의 읽기가능한 바이트 수
while((data=s.read(buf))!= -1) {
fos.write(buf,0,data);
//File예제.txt에 내용을 출력해보자
}
fos.flush();
fos.close();
s.close();
}
}
파일의 리스트를 모두 vector안에 넣는다
그 Vector<InputStream>을
SequenceInputStream에 넣어줘 하나의 Stream으로 합친다.
그 후 FileOutputStream로 파일을 만들어 저장
(FileWriter 등으로
6) @@ 쓰레드 @@
쓰레드 : 하나의 프로세서에서
여러개의 작업을 하게 만들어줌
Runnable의 run()메서드를 사용해
Thread에 넣어줌.,
쓰레드의 이름을 정하지않고 실행 시 Thread-0 과 같이 숫자로 분류해줌
하나의쓰레드가 sleep상태에들어가면 다음 쓰레드가 동작을 하게 됨
package ex1_create;
public class Exam1 {
public static void main(String[] args) {
System.out.println(Thread.currentThread().getName()+"시작");//main쓰레드
Runnable f; //Runnable은 함수적인터페이스임(추상메서드가 1개)
//매개변수가없고 리턴값도없음!!
f=()->{
for (int i = 0; i < 5; i++) {
System.out.println(i+":"+Thread.currentThread().getName());
try {
Thread.sleep(1000);//대기상태(멀티쓰레드사용을 위해)
}
catch(InterruptedException e) {}
}
};
Thread t1 = new Thread(f,"하하");
Thread t2 = new Thread(f);
t1.start();t2.start();
System.out.println(Thread.currentThread().getName()+"종료");
}
}
main시작
main종료
0:Thread-0
0:하하
1:Thread-0
1:하하
2:Thread-0
2:하하
3:하하
3:Thread-0
4:Thread-0
4:하하
@@ 6-1) 쓰레드의 동기화 @@
동기화방법은 크게 2가지가존재
1. 동기화메서드 사용
2. 동기화블럭 사용
동기화블럭 사용 예
package ex2_synchronized;
class SyThred extends Thread{
private static Object Lock = new Object();
private String name;
public SyThred(String name) {
super(name);//부모생성자에 이름을 넘김
}
@Override
public void run() {
synchronized (Lock) {
for (int i = 0; i < 5; i++) {
System.out.println(i+"::"+Thread.currentThread().getName());
//현재쓰레드의 이름
}
}
}
}
public class Ex1_block {
public static void main(String[] args) {
SyThred s1 = new SyThred("하하");
SyThred s2 = new SyThred("동곤자바");
s1.start();
s2.start();
}
}
0::하하
1::하하
2::하하
3::하하
4::하하
0::동곤자바
1::동곤자바
2::동곤자바
3::동곤자바
4::동곤자바
동기화 메서드 사용 예
* 2. 동기화 메서드방식
* 메서드에 synchronized 예약어사용
* (메서드를 lock으로사용함)
* 동기화메서드는유일해야한다.
* 공유객체의 메서드여야한다.
class PrintThread3 extends Thread{
Printer prt;
char ch;
PrintThread3(Printer prt , char ch){
this.prt = prt;
this.ch = ch;
}
@Override
public void run() {
for (int i = 0; i < 5; i++) {
prt.printChar(ch);
}
}
}
//------------------------------------------------------------
class Printer{
public synchronized void printChar(char ch) {//동기화메서드
for (int i = 0; i < 5; i++) {
System.out.print(ch);
}System.out.println();
}
}
public class PrintThreadEx3 {
public static void main(String[] args) {
Printer p = new Printer();
PrintThread3 t1 = new PrintThread3(p, 'A');
PrintThread3 t2 = new PrintThread3(p, 'B');
PrintThread3 t3 = new PrintThread3(p, 'C');
t1.start();t2.start();t3.start();
}
}
AAAAA
AAAAA
AAAAA
AAAAA
AAAAA
CCCCC
CCCCC
CCCCC
CCCCC
CCCCC
BBBBB
BBBBB
BBBBB
BBBBB
BBBBB
6-2) Daemon 쓰레드
데몬 스레드
* 1.일반스레드의 보조기능담당
* 2.일반스레드가 종료되면 데몬스레드도 종료
* 3.가비지콜렉터가 대표적인 데몬스레드
* 4.무한반복형태로구현
setDaemon(true) 로 데몬쓰레드설정을 해줌
package ex4_daemon;
class DaemonThread extends Thread {
public DaemonThread(String name) {
super(name);
}
@Override
public void run() {
int i =1;
while (true) {
System.out.println(i++ +":"+Thread.currentThread().getName());
try {
sleep(100);//sleep 상태 동안 다른쓰레드 실행
} catch (InterruptedException e) {
}
}
// run()의 while문은 break문없이
// 무한으로 this를 출력한다
}
}
//----------------------------------------------------------------------------
public class DaemonEx1 {
public static void main(String[] args) throws InterruptedException {
System.out.println(Thread.currentThread().getName() + "스레드 시작");
DaemonThread t1 = new DaemonThread("쓰레드1");
DaemonThread t2 = new DaemonThread("쓰레드2");
t1.setDaemon(true);
t2.setDaemon(true);// 데몬스레드로지정
t1.start();
t2.start();
Thread.sleep(1000);// mainThread를 1초간 sleep 후 종료 --> DaemonThread도 종료
System.out.println(Thread.currentThread().getName() + "스레드 종료");
}
}
main스레드 시작
1:쓰레드1
1:쓰레드2
2:쓰레드1
2:쓰레드2
3:쓰레드1
3:쓰레드2
4:쓰레드1
4:쓰레드2
5:쓰레드2
5:쓰레드1
6:쓰레드2
6:쓰레드1
7:쓰레드2
7:쓰레드1
8:쓰레드2
8:쓰레드1
9:쓰레드2
9:쓰레드1
10:쓰레드1
10:쓰레드2
main스레드 종료
이론상 Thread는 무한으로 실행될것같다.
하지만 메인Thread(Main)이 종료되면 종료된다
main을 1초정도 sleep을 해뒀는데
그 동안만 실행되고 종료되는것임.
6-3) 쓰레드 정리
* 쓰레드정리
* 1.스레드 생성
* 1) Thread 클래스상속 , run메서드 오버라이딩
* 2) Runnable 인터페이스구현 , run메서드오버라이딩 , Thread객체에 주입
*
* 2.스레드상태
* Thread 생성상태 : new Thread();
* Runnable 상태 : start()메서드 실행 후
* Running 상태 : start()에 의해 run()메서드가 실행중인 상태
*
* 대기상태 : sleep(), 동기화 lock획득실패,
* wait() : notify() or notifyAll로 꺠우지않으면 무한대기
* 대기상태해제시 Runnable상태로 변경
* Dead 상태 : run메서드를 모두 실행하고 종료된 상태
*
* 3.주요메서드
* (1) start() : 병렬화 기능 , run메서드 호출 , new 상태-->Runnable상태
* (2) run() : 쓰레드의기능 , 스레드가 실행하는 메서드.
* (3) sleep(ms) : 밀리초만큼 대기
* (4) setDaemon(boolean) : true인경우 DaemonThread로 사용하곘단소리
* (start전에 실행) Daemon스레드 :일반 스레드종료시 함께종료
* (5) join() : 해당스레드가 종료시까지 호출한메서드가 대기
* (6) setPriority(1~10) : 우선순위설정
* (7) interrupt() : InterruptedException발생시킴
* (8) stop()메서드는 쓰지마라.
*
* 4.동기화 : Synchronized 예약어사용
* 동기화블럭 : lock설정 , 공유객체로 lock설정해야함
* 동기화메서드 :공유객체의 메서드여야함(유일해야함)
* 메서드자체가 동기화영역
*
* 5.wait , notify , notifyAll
* Object 멤버
* 동기화영역에서만 사용 가능
7) @@ Function 패키지 @@
7-1) Consumer 인터페이스
consumer인터페이스는 매개변수가있으며 리턴값이 없음
accept를 통해 구현한 인터페이스를 사용가능함!!
예제로 보여주겠음
package ex1_conumer;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.function.DoubleConsumer;
import java.util.function.IntConsumer;
import java.util.function.ObjIntConsumer;
public class MyEx {
public static void main(String[] args) {
Consumer<String> f1= (t)->System.out.println(t+" !!출력!!");
f1.accept("하하");
BiConsumer<String, Integer> f2 = (s,i)->System.out.println(s+"는"+i+"살");
f2.accept("유동곤", 26);
DoubleConsumer f3 = (s)->System.out.printf(s+" + 20 : %.3f \n",(s+20));
f3.accept(10.56);
IntConsumer f4 = (s)->{
int sum=0;
for (int j = 1; j <= s; j++) {
sum+=j;
}System.out.println("1부터"+s+"의 합 : "+sum);};
f4.accept(10);
ObjIntConsumer<String> f5 = (s,i)->{System.out.println(s+"는 "+i+"번째 손님");};
f5.accept("하하", 10);
}
}
하하 !!출력!!
유동곤는26살
10.56 + 20 : 30.560
1부터10의 합 : 55
하하는 10번째 손님
7-2) Suplier 인터페이스
T getXXX() : 매개변수가없으며 리턴값이 존재
* Supplier<T> : T get()
* IntSupplier : int getAsInt()
* DoubleSupplier : double getAsDouble()
* BooleanSupplier : boolean getAsBoolean()
package ex2_Supplier;
import java.util.Iterator;
import java.util.function.IntSupplier;
import java.util.function.Supplier;
public class Myex {
public static void main(String[] args) {
Supplier<String> s =()->"java";
System.out.println(s.get());
IntSupplier s2 = ()->{
System.out.println("@@1부터100까지의합@@");
int sum=0;
for (int i = 0; i <= 100; i++) {
sum+=i;
}
return sum;
};
System.out.println(s2.getAsInt());
}
}
java
@@1부터100까지의합@@
5050
'주말공부 or 복습' 카테고리의 다른 글
주말복습 7( HTML) (0) | 2025.03.16 |
---|---|
주말복습6 (DB) (2) | 2025.03.09 |
주말복습4(Collection(List,set,Map) (0) | 2025.03.01 |
주말복습3(접근제어자 , 인터페이스,내부클래스, 예외처리) (0) | 2025.02.23 |
주말 복습 2 ( 클래스와 생성자, 상속) (2) | 2025.02.15 |