えいあーるれいの技術日記

ROS2やM5 Stack、Ubuntuについて書いています

Rustを使ってみた(Ubuntu 20.04)

みなさんはRustというプログラミング言語を知っていますか?

f:id:Ray_ar:20210804104337p:plain

Rustとは、2010年頃に登場したプログラミング言語で、性能、メモリ安全性、安全な並行性を目指して設計されたマルチパラダイムプログラミング言語と言われています。(Wikipediaより参照)

C言語C++などのプログラミング言語に置きかわる言語として注目されており、Linuxカーネルの構成プログラムにも採用されるとかされないとか言われています。

最近は組み込みにもRustが使われるという事例も増えているので、低レイヤ層の開発者が特に注目しているものと思われます。

www.nikkei.com

日経記事は「パイソン」を使う高スキルITエンジニアが「ラスト」に注目していると取り上げており、これから参入するエンジニアも多いのではないでしょうか❓

私はC++Pythonを使っており、Rustを学ぶ意味はあまりないのかなーーと感じています。

しかし、食わず嫌いも良くないと思っているのでとりあえず手を出してみることにしました。

コーディングした感想としては、以外にも悪くないなーーと思える点もあったので、紹介していきたいと思います。

対象になったリポジトリ

私が現在コーディングしているIP4-detectorというリポジトリがあるので、そのソースコードを移植しました。

このプログラムの解説は後々Qiitaに投稿しようと思っています。

github.com

このプログラムを実行すると、実行後にIPアドレス(v4)を表示します。

show_ip4は引数にネットワークアダプタを指定して対象のアダプタのIPアドレスを取得します。

show_ip4_allは全てのネットワークアダプタを検出してリストあるいはベクターとして取得します。

いずれも文字列で取得します。

#(例1)
$ ./show_ip4 docker0
> 172.17.10.1

#(例2)
$ ./show_ip4_all
> ["192.168.0.10" , "172.17.10.1"]

環境構築

簡単だけど、aptでインストールできないんかい!

$ curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
> (オプションについて選択肢が提示されるので1を入力)
> 1
> ...
> Rust is installed now. Great!
> 
> To get started you may need to restart your current shell.
> This would reload your PATH environment variable to include
> Cargo's bin directory ($HOME/.cargo/bin).
> 
> To configure your current shell, run:
> source $HOME/.cargo/env

www.rust-lang.org

ちなみに、Rustの環境はインストール後に~/.bashrcに書き込まれるので再度環境を読み込めば晴れてRustデビューです🎉

cargoを使う

RustはCargoというビルドツール兼パッケージマネージャを使います。CやC++におけるCMakeとほとんど似た役割を持っています。

CMakeと比べて便利なところといえば、PythonにおけるPyPiのようにパッケージを管理するサイトがあり、pipのようにビルド実行時に勝手に対応するバージョンをインストールするところです。

ソースコードの依存関係をできる限り分かりやすく記述することができるので、Rustの開発環境には不可欠です。Cargo.tomlというファイルがCMakeにおけるMakefileのようなファイルに当たります。

ワークスペースの作成

ワークスペースは次のコマンドで作成します。例えば<workspace name>ワークスペースを作成するときは、

$ cargo new <workspace name>でOKです。

作成されたワークスペースは次のような、show_ip4におけるファイル構造は次のようになっています。

show_ip4
├── Cargo.toml
└── src
    └── main.rs

src以下にプログラムを記述していきます。

実行

実行はとても簡単。対象のワークスペース内に入ってcargo run <args>です。1度目のビルドのみ時間がかかります。ビルドを行うと、Cargo.locktarget/というファイルが生成されます。GitHubに上げる場合は.gitignoreで除外しておきましょう。

ビルド済ファイルは、<workspace name>/target/debug/以下に<workspace name>と同じ名称の実行ファイルがあり、コレを直接呼び出すことでも動きます。

プログラミング基本構文について

今回の実装ではクラスが登場していないのであまり本質的なところについては分かっていませんが、触った感想としては、「Pythonに少し近づいたC++」だと思いました。

次は、面白いな〜とおもった構文を紹介します。

変数は宣言するが、型は推論される

C++のように宣言しますが、letというキーワードのみを使い、intやstringなどは自動で推論します。ただし、letのみでは内容の変更が不可能であるため、let mutというキーワードを使用します。その他の使い方についてはリファレンスを見てみてください。

// 変更不可な変数宣言
let a = 0;
// 変更可能な変数宣言
let mut b = 0;
b = 1;

関数宣言はPython風、だけど強制力がある。

Pythonは引数と返り値を自由に設定でき、型はPython3.5以降だと指定することができます。(Type Hints機能)

# Pythonの例
def abc(a : str) -> str :
    # 中略
    return b

RustではPythonのような引数と返り値を持ちますが、その型については必ず指定する必要があります。

// Rustの例
fn abc(a: &str) -> String {
    // 中略
    return b
}

その他は基本的にPythonの機能もサポートしているように見えるC++という箇所が多い気がしました。いろいろな構文に影響を受けている点もあり、初見だと結構面倒に感じました。

私は、String関連で結構つまづきました…

まとめ

Pythonなどに近い形をとった文法でありながらちゃんとバイナリファイルが生成されるので、これは慣れたらかなり心強い環境であると感じました。C++Pythonをある程度書けるなら、1日程度文法を見直せば移行できそうです。

ただし、C++Pythonほどドキュメントは充実していないのでサイトのコピペを期待することは難しそうです。実際、Copilotはあまり役に立ちませんでした。ROSでは結構活躍したんだけどなぁ…

ar-ray.hatenablog.com

C/C++くらい資源が増えれば間違いなく置き換わってしまうんじゃないかと感じるくらいには可能性を感じているので、Rustについてもっと勉強しようと思います。