異なる表現

// Copyright 2026 Google LLC
// SPDX-License-Identifier: Apache-2.0

fn main() {
    let c_repr = b"Hello, C\0";
    let cc_repr = (b"Hello, C++\0", 10u32);
    let rust_repr = (b"Hello, Rust", 11);
}

各言語には物事の実装方法について独自の考え方があり、それが混乱やバグにつながることがあります。テキストを表現する 3 つの方法を考えてみましょう。

生の表現を Rust の文字列スライスに変換する方法を示してください:

// Copyright 2026 Google LLC
// SPDX-License-Identifier: Apache-2.0

// C 表現から Rust へ
unsafe {
    let ptr = c_repr.as_ptr() as *const i8;
    let c: &str = std::ffi::CStr::from_ptr(ptr).to_str().unwrap();
    println!("{c}");
};

// C++ 表現から Rust へ
unsafe {
    let ptr = cc_repr.0.as_ptr();
    let bytes = std::slice::from_raw_parts(ptr, cc_repr.1);
    let cc: &str = std::str::from_utf8_unchecked(bytes);
    println!("{cc}");
};

// Rust 表現(バイト列)から文字列スライスへ
unsafe {
    let ptr = rust_repr.0.as_ptr();
    let bytes = std::slice::from_raw_parts(ptr, rust_repr.1);
    let rust: &str = std::str::from_utf8_unchecked(bytes);
    println!("{rust}");
};

余談: Rust には c プレフィックス付きの文字列リテラルがあります。これは末尾に null バイトを追加します。たとえば c"Rust" == b"Rust\0" です。