C.W.K.
Stream
Lesson 01 of 05 · published

스레드 & join

~10 min · concurrency, threads, spawn, join

Level 0Rust 호기심러
0 XP0/80 lessons0/19 achievements
0/100 XP to next level100 XP to go0% complete

Rust 의 간판 약속이 'fearless concurrency' 야 — 마케팅이 아니야. 컴파일러가 데이터 레이스를 정적으로 막아서, '내 컴퓨터선 되는데 프로덕션선 데이터 망가짐' 스레딩 버그 부류 전체가 아예 컴파일 안 돼. 이 트랙이 그 방법을 보여줘.

스레드 spawn 하기

thread::spawn 은 클로저를 받아 새 OS 스레드에서 돌리고 JoinHandle 을 반환해. 새 스레드는 spawn 한 스레드랑 동시에 돌아. 얘들은 진짜 OS 스레드야 (green thread 아님) — 가벼운 async 동시성은 다음 트랙이야.

join: 완료 기다리기

spawn 한 스레드는 자식을 자동으로 안 기다려. 핸들에 .join() 을 불러 그 스레드가 끝날 때까지 블록하고 결과를 모아. join 까먹으면 main 이 스레드 실행 중에 종료할 수 있어 — 작업 중에 죽여져. join 이 '계속하기 전에 이 스레드 작업이 필요해' 라고 말하는 법이야.

스레드는 동시에 돌고; join 이 동기화 지점이야. 병렬로 일하려고 spawn, 기다리고 모으려고 join. spawn 이 반환한 핸들이 스레드로의 유일한 연결이야 — 기다려야 하면 들고 있고, 스레드가 친 panic 을 드러내려면 .join().unwrap().

컴파일러가 지켜보는 것

클로저가 데이터를 캡처해 다른 스레드로 move 하는 순간, borrow checker 의 일이 어려워져: 두 스레드가 같은 데이터를 동시에 건드릴 수 있거든. Rust 의 답은 SendSync trait (이 트랙 마지막 레슨) 인데, 컴파일러가 네 공유가 race-free 임을 컴파일 타임에 증명하게 해줘. 여기 모든 게 그 보장 위에 서.

Code

스레드 spawn, join 으로 결과 모으기·rust
use std::thread;

fn main() {
    let handle = thread::spawn(|| {
        for i in 1..=3 {
            println!("worker: {i}");
        }
        42 // 스레드도 값을 반환할 수 있어
    });

    println!("main keeps running");

    // join 은 스레드가 끝날 때까지 블록하고 반환값을 내놔
    let result = handle.join().unwrap();
    println!("thread returned {result}");
}

External links

Exercise

각각 다른 숫자의 제곱을 계산해 반환하는 스레드 셋을 spawn 해. 핸들을 Vec 에 모으고, 각각 join 하고, 결과를 합산해. 출력 순서는 어떻게 되고, 왜 거기 의존하면 안 돼?
Hint
스레드는 동시에 도니까 출력 순서가 비결정적이야 — OS 스케줄러가 정해. 근데 순서대로 join 하고 반환값을 모으면 실행 순서와 무관하게 결정적 결과를 얻어.

Progress

Progress is local-only — sign in to sync across devices.
이 페이지에서 버그를 발견하셨거나 피드백이 있으세요?문제 신고

댓글 0

🔔 답글 알림 (로그인 필요)
로그인댓글을 남기려면 로그인해 주세요.

아직 댓글이 없어요. 첫 댓글을 남겨보세요.