2.2. 変数と基本型

変数は、= 演算子で値に結び付ける名前です。代入後は、その値が使える場所ならどこでもその名前を使えます:

width = 320
height = 240
pixels = width * height
print(pixels)               # prints 76800

= の右辺がまず評価され、その結果が左辺の名前に束縛されます。一度も代入されていない名前を読むと NameError が発生します。

変数は単なるラベルです。値を指し示すものであり、値そのものはどこか別の場所にあって、同じ値にいくつでもラベルを付けられます。

3つのラベルが箱に入った3つの値を指している様子。ラベルを再代入すると、 値ではなく矢印が動く。

変数は値を指すラベルです。変数を再代入するとラベルが移動するだけで、そのラベルが以前指していた値は変わりません。

2.2.1. 命名規則

  • 名前は文字またはアンダースコアで始まり、文字、数字、アンダースコアを含めることができます。frame_count_internal は問題ありませんが、1st_frame は構文エラーです。

  • 名前は大文字と小文字を区別します。Widthwidth は別々の2つの変数です。

  • liststrid()print() などの組み込み名の再利用は避けてください。それらを覆い隠してもエラーにはなりませんが、スクリプトの残りの部分では元の組み込みにアクセスできなくなります。

  • 慣例: 変数と関数には snake_case、変更するつもりのない定数には ALL_CAPS、クラス名には CamelCase を使います。

2.2.2. 基本型

Pythonのすべての値には、それがサポートする操作を決めるがあります。もっともよく書くことになる4つの型は次のとおりです:

  • int -- 正または負の整数。MicroPythonの整数はメモリが許す限り大きくなります。リテラルは単なる数字として書きます: 042-7。16進数(0x1A)、8進数(0o17)、2進数(0b1010)のリテラルも有効で、レジスタやビットマスクに便利です。

  • float -- 小数点または指数を持つ数値: 3.141.0-0.52e6(= 2,000,000.0)。カメラ上のすべてのfloatはIEEE 754の32ビットで、有効数字約7桁の精度があります。

  • bool -- 2つのリテラル True または False のいずれか(大文字に注意)。

  • str -- テキスト。シングルクォートまたはダブルクォートで囲んだ文字として書きます: "hello"'OpenMV'。どちらのクォートスタイルも同等です。文字列内に現れるクォート文字をエスケープせずに済む方を選びましょう。

すぐに知っておく価値のある5つ目の値もあります:

  • None -- NoneType 型の唯一の値。「値がない」または「まだ設定されていない」ことを意味するために使われます。明示的に何も返さない関数は、暗黙的に None を返します。

2.2.3. 型の確認と変換

組み込みの type() 関数は、任意の値の型を返します:

>>> type(42)
<class 'int'>
>>> type(3.14)
<class 'float'>
>>> type("hello")
<class 'str'>

各型は変換関数としても機能します。異なる型の値を渡すと、変換が明確に定義されている場合に、新しい型の同等の値が返されます:

>>> int("42")
42
>>> int(3.9)
3                           # truncates toward zero, not rounds
>>> float("1.5")
1.5
>>> str(255)
'255'
>>> bool(0), bool(1), bool("")
(False, True, False)

明確に定義されていない変換は ValueError を発生させます:

>>> int("hello")
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: invalid syntax for integer with base 10

2.2.4. 再代入と動的型付け

名前はいつでも任意の型の値に再代入できます。次のコードは正当です:

x = 42
x = "now I'm a string"
x = 3.14

Pythonは変数を型に束縛しません。x が整数であることに依存するコードは、それを使う時点で整数を期待しているだけです。別のものが渡されると、実行時に TypeError が発生します。

注釈

x を再代入しても、古い束縛が指していた値は 変わりません。2つの名前が同じ値を共有している場合、一方を再代入してももう一方には影響しません:

a = [1, 2, 3]
b = a                       # both point at the same list
a = "different now"
print(b)                    # still [1, 2, 3]

共有された値を変更するのは別の話です。list.append のようなメソッドは束縛が指す値そのものを変更するため、その同じ値を指す他のすべての名前にも変更が見えます。