Python の 35,000 倍速いプログラミング言語 Mojo🔥 とは

[Mojo🔥](https://www.modular.com/mojo)とは、[LLVM](https://llvm.org/) や [Swift](https://www.apple.com/jp/swift/) の生みの親として知られる Chris Lattner 氏が率いる [Modular 社](https://www.modular.com/)が開発した新しい汎用プログラミング言語です。
Python 互換の使いやすい構文と C 言語並みの処理速度を特徴とし、AI 開発に利用されることが期待されています。

## Mojo の特徴

- Python 互換の構文を持っている。
- 動的型付けと静的型付けの両方の構文を持っている。
- 処理速度が C 言語並みに速い。
- [コンパイル型言語](https://ja.wikipedia.org/wiki/%E3%82%B3%E3%83%B3%E3%83%91%E3%82%A4%E3%83%AB%E5%9E%8B%E8%A8%80%E8%AA%9E)である。
- [システムプログラミング言語](https://ja.wikipedia.org/wiki/%E3%82%B7%E3%82%B9%E3%83%86%E3%83%A0%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0%E8%A8%80%E8%AA%9E)である。
- 中間表現に [MLIR](https://mlir.llvm.org/) を採用している。

## 開発環境

クラウド型の開発環境である [Mojo Playground](https://playground.modular.com/) または [Mojo SDK](https://developer.modular.com/download) を利用することができます。

- Mojo Playground
![スクリーンショット 2023-05-22 19.38.51.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/127532/53eaed88-3a11-6d32-fddd-85ffdf64fa71.png)

https://playground.modular.com/

- Mojo SDK

https://developer.modular.com/download


## Hello World!

Mojo は Python 互換の構文を持っているため、簡単なコードであれば Python のコードをそのまま実行することできます。

```python
print("Hello Mojo!")
```

# let と var

Mojo は Python と同様に変数を宣言し、値を代入することができますが、以下の 2 つの課題が残ります。

1. 値がイミュータブル（不変）であることを宣言したい。
1. 代入時に変数名を誤って入力した場合はエラーとしたい。

これらの課題を解決するために、**let** と **var** の宣言をサポートしています。
**let** はイミュータブル（不変）、**var** はミュータブル（可変）の変数を宣言します。

```python
def your_function(a, b):
    let c = a
    # Uncomment to see an error:
    # c = b  # error: c is immutable

    if c != b:
        let d = b
        print(d)

your_function(2, 3)
```

## struct

**struct** は Python の **class** とよく似ていますが、いくつか違いがあります。

- すべてのプロパティを **var** または **let** で宣言する必要があります。これにより、オーバーヘッドなしでプロパティにアクセスできるようになります。
- 静的に宣言されるため、実行中にメソッドの追加や削除はできません。

```python
struct MyPair:
    var first: Int
    var second: Int

    # We use 'fn' instead of 'def' here - we'll explain that soon
    fn __init__(inout self, first: Int, second: Int):
        self.first = first
        self.second = second

    fn __lt__(self, rhs: MyPair) -> Bool:
        return self.first < rhs.first or
              (self.first == rhs.first and
               self.second < rhs.second)
```

## fn

**fn** は Python の **def** とよく似ていますが、いくつか違いがあります。

- 引数は型指定が必要となる。
- 引数はイミュータブル（不変）となる。
- 戻り値の型が指定されていない場合は、**None** が指定されたものと見なされる。
- 関数内のローカル変数は **let** または **var** で宣言する必要がある。

```python
struct Complex:
    var re: F32
    var im: F32

    fn __init__(inout self, x: F32):
        """Construct a complex number given a real number."""
        self.re = x
        self.im = 0.0

    fn __init__(inout self, r: F32, i: F32):
        """Construct a complex number given its real and imaginary components."""
        self.re = r
        self.im = i
```

## 強力な型チェック

Python と同様に動的型付けを使用することもできますが、強力な型チェックを利用することもできます。

```python
def pairTest() -> Bool:
    let p = MyPair(1, 2)
    # Uncomment to see an error:
    # return p < 4 # gives a compile time error
    return True
```

## Python モジュールの利用

**Python.import_module** を使って簡単に Python モジュールを利用することができます。

```python
def make_plot(m: Matrix):
    np = Python.import_module("numpy")
    plt = Python.import_module("matplotlib.pyplot")
    colors = Python.import_module("matplotlib.colors")
    dpi = 64
    width = 10
    height = 10 * yn // xn

    fig = plt.figure(1, [width, height], dpi)
    ax = fig.add_axes([0.0, 0.0, 1.0, 1.0], False, 1)

    light = colors.LightSource(315, 10, 0, 1, 1, 0)

    image = light.shade(m.to_numpy(), plt.cm.hot, colors.PowerNorm(0.3), "hsv", 0, 0, 1.5)
    plt.imshow(image)
    plt.axis("off")
    plt.show()

make_plot(compute_mandelbrot())
print("finished")
```

## さいごに

Python と Mojo の関係は、C と C++ の関係に似ています。
Mojo は Python のスーパーセットを目指して開発が進められており、段階的な置き換えができるようになるでしょう。

現在の AI 開発では、Python の他に C、C++、Cython、CUDA など複数のプログラミング言語が使用されますが、一般的なデバッガは複数のプログラミング言語を跨いでデバッグすることができません。
もし Mojo だけで AI 開発を完結できるようになれば、生産性が大きく改善するでしょう。

注意点として、Mojo はまだ未完成のプログラミング言語であり、現時点では完全な Python 互換ではありません。
また、処理速度を大幅に向上させるには、Python コードをそのまま移植するだけでなく、静的なコードに書き換えるなどの最適化が必要になります。

Mojo はまだ開発の初期段階ですが、大きなポテンシャルを持っていると感じています。
[Mojo Playground](https://playground.modular.com/) では、チュートリアルも用意されていますので、ぜひ一度触ってみてください。

https://docs.modular.com/mojo/