hyunsu blog

홈강좌Rust 입문·중급 47편 중 40편째

Rust 모듈 — mod 로 나누고 pub 로 열고 use 로 불러온다

목차 · 3
  1. 01mod 로 묶고 pub 으로 연다
  2. 02pub 이 없으면 E0603
  3. 03실습 — 모듈을 파일로 나누기

Rust 모듈은 mod 이름 { } 으로 코드를 묶는 단위다. 모듈 안의 것은 기본이 비공개라서, 밖에서 쓰려면 pub 을 붙여야 하고 아니면 E0603 이 난다. use 로 긴 경로를 줄이고, mod 이름; 한 줄로 내용을 src/이름.rs 파일로 옮긴다.

01 mod 로 묶고 pub 으로 연다

가격 계산 함수들을 pricing 모듈로 묶어 보자.

rust
mod pricing {
    pub fn with_tax(price: u32) -> u32 {
        price + tax(price)
    }

    fn tax(price: u32) -> u32 {
        price / 10
    }
}

fn main() {
    println!("{}", pricing::with_tax(12000));
}
text
   Compiling shop v0.1.0 (~/projects/shop)
    Finished `dev` profile [unoptimized + debuginfo] target(s) in 0.15s
     Running `target/debug/shop`
13200
  • mod pricing { … } 안의 함수들은 pricing 모듈에 속한다.
  • 밖에서는 pricing::with_tax 처럼 모듈 이름과 :: 로 부른다. 29편의 std::collections::HashMap 도 이런 경로다(std 안의 collections 안의 HashMap).
  • with_tax 앞의 pub 은 "모듈 밖에서도 쓸 수 있다" 는 뜻이다.
  • tax 에는 pub 이 없다. 모듈 안(같은 pricing 의 with_tax)에서만 쓸 수 있다.

02 pub 이 없으면 E0603

밖에서 tax 를 직접 불러 보자.

rust
mod pricing {
    pub fn with_tax(price: u32) -> u32 {
        price + tax(price)
    }

    fn tax(price: u32) -> u32 {
        price / 10
    }
}

fn main() {
    println!("{}", pricing::tax(12000));
}
text
error[E0603]: function `tax` is private
  --> src/main.rs:12:29
   |
12 |     println!("{}", pricing::tax(12000));
   |                             ^^^ private function
   |
note: the function `tax` is defined here
  --> src/main.rs:6:5
   |
 6 |     fn tax(price: u32) -> u32 {
   |     ^^^^^^^^^^^^^^^^^^^^^^^^^
  1. 무엇 — 함수 tax 는 비공개(private)다.
  2. 어디 — 12번째 줄 pricing::tax. note: 가 6번째 줄의 정의를 보여 준다.
  3. 고치는 법 — help: 는 없다. 밖에서 써야 한다면 정의에 pub 을 붙이고, 아니면 공개된 with_tax 를 쓴다.

기본이 비공개인 것은 3편의 "기본이 불변" 과 같은 생각이다. 밖에서 써도 되는 것만 골라 pub 으로 열면, 안쪽은 마음대로 고쳐도 바깥 코드가 깨지지 않는다.

03 실습 — 모듈을 파일로 나누기

모듈이 길어지면 파일로 뺀다. src/main.rs 에는 한 줄만 남긴다.

rust
mod pricing;

use pricing::with_tax;

fn main() {
    println!("{}", with_tax(12000));
    println!("{}", pricing::discount(12000, 20));
}

내용은 같은 폴더의 src/pricing.rs 로 옮긴다. 이 파일에는 mod pricing { } 껍데기를 쓰지 않는다. 파일 자체가 모듈이다.

rust
pub fn with_tax(price: u32) -> u32 {
    price + price / 10
}

pub fn discount(price: u32, percent: u32) -> u32 {
    price - price * percent / 100
}
text
   Compiling shop v0.1.0 (~/projects/shop)
    Finished `dev` profile [unoptimized + debuginfo] target(s) in 0.16s
     Running `target/debug/shop`
13200
9600
  • mod pricing; 은 "pricing 모듈의 내용은 src/pricing.rs 에 있다" 는 뜻이다. 세미콜론으로 끝난다.
  • use pricing::with_tax; 는 경로를 불러와서 그 뒤로는 with_tax(…) 만 쓰게 한다. 29편에서 HashMap 을 부른 것과 같다.
  • use 하지 않은 discount 는 pricing::discount 로 경로를 다 쓴다. 둘 다 된다.

모듈은 몇 겹이든 겹칠 수 있다. 폴더 src/pricing/ 안에 파일을 두는 식이다. 47편의 wordfreq 2판은 세는 부분을 모듈로 빼서 main.rs 를 짧게 만든다. 다음 편은 남이 만든 코드, 크레이트를 가져다 쓰는 법이다.