3. 形式ばらない Python の紹介
*****************************

以下の例ではプロンプト (*>>>* と *...*) の有無で入力と出力を区別します
。例を試すには、プロンプトが表示されているときに例のプロンプトより後ろ
の内容をすべて入力してください。プロンプトで始まらない行はインタープリ
タの出力です。例の中で二次プロンプトだけがある行は、空行を入力すること
を意味します。この空行で複数行にわたるコマンドの入力を終えます。

対話プロンプトで入力する例も含め、このマニュアルの多くの例にはコメント
が付いています。Python のコメントはハッシュ文字 "#" で始まり、物理行の
末尾まで続きます。コメントは行の先頭や空白・コードの後に書けますが、文
字列リテラルの中には書けません。文字列リテラル内のハッシュ文字は単なる
ハッシュ文字です。コメントはコードをわかりやすくするためのもので、
Python は解釈しません。そのため、例を入力するときには省略できます。

いくつかの例です:

   # これは最初のコメント
   spam = 1  # そしてこれは2つめのコメント
             # ...そして3つめ!
   text = "# これはクォーテーションの間なのでコメントではない。"


3.1. Python を電卓として使う
============================

簡単な Python コマンドをいくつか試してみましょう。インタープリタを起動
し、一次プロンプト ">>>" が表示されるのを待ちます。(すぐに表示されるは
ずです。)


3.1.1. 数
---------

インタープリタは簡単な電卓のように動作し、式を入力するとその値を表示し
ます。式の構文は単純です。演算子 "+" 、 "-" 、 "*" 、 "/" で算術演算を
行い、丸括弧 ("()") で式をまとめられます。例えば次のように使います:

   >>> 2 + 2
   4
   >>> 50 - 5*6
   20
   >>> (50 - 5*6) / 4
   5.0
   >>> 8 / 5  # 除算は常に浮動小数点数を返す
   1.6

整数 (例えば "2" 、 "4" 、 "20") は "int" 型で、小数部を持つ数 (例えば
"5.0" 、 "1.6") は "float" 型です。数値型についてはこのチュートリアル
の後の節で詳しく説明します。

除算 ("/") は常に浮動小数点数を返します。 *切り捨て除算* で整数の結果
を得るには "//" 演算子を使います。剰余は "%" で求められます:

   >>> 17 / 3  # 除算は浮動小数点数を返す
   5.666666666666667
   >>>
   >>> 17 // 3  # 切り捨て除算は小数部を切り捨てる
   5
   >>> 17 % 3  # % 演算子は剰余を返す
   2
   >>> 5 * 3 + 2  # 切り捨てられた商 * 除数 + 剰余
   17

Python では "**" 演算子で冪乗を計算できます [1]:

   >>> 5 ** 2  # 5の2乗
   25
   >>> 2 ** 7  # 2の7乗
   128

等号 ("=") は変数に値を代入するときに使います。代入後は結果を表示せず
に次の対話プロンプトに進みます:

   >>> width = 20
   >>> height = 5 * 9
   >>> width * height
   900

「定義」されていない (値が代入されていない) 変数を使おうとするとエラー
になります:

   >>> n  # 未定義の変数にアクセスする
   Traceback (most recent call last):
     File "<stdin>", line 1, in <module>
   NameError: name 'n' is not defined

浮動小数点数も全面的にサポートしています。整数と浮動小数点数が混在する
演算では、演算子が整数のオペランドを浮動小数点数に変換します:

   >>> 4 * 3.75 - 1
   14.0

対話モードでは最後に表示された式の値が変数 "_" に代入されます。この変
数を使うと、Python を電卓として使うときに続きの計算が少し楽になります
。例えば次のように使います:

   >>> tax = 12.5 / 100
   >>> price = 100.50
   >>> price * tax
   12.5625
   >>> price + _
   113.0625
   >>> round(_, 2)
   113.06

この変数は読み取り専用として扱い、明示的に値を代入しないでください。代
入すると同じ名前の別のローカル変数が作られ、特別な動作をする組み込み変
数が隠されてしまいます。

Python は "int" と "float" のほかに、 "Decimal" や "Fraction" などの数
値型もサポートしています。 複素数 も組み込みでサポートしており、接尾辞
"j" または "J" で虚部を表します (例: "3+5j")。


3.1.2. テキスト
---------------

Python は数値だけでなくテキストも扱えます。テキストは "str" 型で表され
、一般に「文字列」と呼ばれます。 ""!"" のような文字、 ""rabbit"" のよ
うな単語、 ""Paris"" のような名前、 ""Got your back."" や ""Yay! :)""
のような文や表現などです。文字列はシングルクォート ("'...'") またはダ
ブルクォート (""..."") で囲み、どちらを使っても同じ結果になります [2]
。

   >>> 'spam eggs'  # シングルクォート
   'spam eggs'
   >>> "Paris rabbit got your back :)! Yay!"  # ダブルクォート
   'Paris rabbit got your back :)! Yay!'
   >>> '1975'  # クォートに囲まれた数字も文字列
   '1975'

文字列を囲むクォートと同じクォートを文字列の中に書くには、直前に "\"
を付けて「エスケープ」します。別の種類のクォートで文字列を囲む方法もあ
ります:

   >>> 'doesn\'t'  #  \' を使用してシングルクォートをエスケープする
   "doesn't"
   >>> "doesn't"  # または代わりにダブルクォートを使用する
   "doesn't"
   >>> '"Yes," they said.'
   '"Yes," they said.'
   >>> "\"Yes,\" they said."
   '"Yes," they said.'
   >>> '"Isn\'t," they said.'
   '"Isn\'t," they said.'

Python シェルでは文字列を定義するときと出力するときで見た目が異なるこ
とがあります。 "print()" 関数は文字列を囲むクォートを省き、エスケープ
された文字や特殊文字を表示して読みやすく出力します:

   >>> s = 'First line.\nSecond line.'  # \n は改行を意味する
   >>> s  # print() を使用しない場合、特殊文字が文字列に含まれる
   'First line.\nSecond line.'
   >>> print(s)  # print() では特殊文字は解釈されるため、\n は改行となる
   First line.
   Second line.

"\" に続く文字を特殊文字として解釈させたくない場合は、最初のクォートの
前に "r" を付けて *raw string* (生の文字列) にできます:

   >>> print('C:\this\name')  # ここでは \t はタブ、\n は改行を表す
   C:      his
   ame
   >>> print(r'C:\this\name')  # クォートの前の r に注目
   C:\this\name

raw string には注意点が1つあります。末尾に奇数個の "\" を連続して置く
ことはできません。詳しい説明と回避方法は FAQ の該当項目 を参照してくだ
さい。

文字列リテラルは複数行にまたがって書けます。1つの方法は三重引用符
(""""..."""" や "'''...'''") を使うことです。改行文字は自動的に文字列
に含まれますが、行末に "\" を付けると改行文字を含めずに済みます。次の
例では最初の改行は含まれません:

   >>> print("""\
   ... Usage: thingy [OPTIONS]
   ...      -h                        Display this usage message
   ...      -H hostname               Hostname to connect to
   ... """)
   Usage: thingy [OPTIONS]
        -h                        Display this usage message
        -H hostname               Hostname to connect to

   >>>

文字列は "+" 演算子で連結し、 "*" 演算子で繰り返せます:

   >>> # 'un' を3回繰り返し、その後に 'ium'
   >>> 3 * 'un' + 'ium'
   'unununium'

2つ以上の *文字列リテラル* (クォートで囲んだもの) を隣り合わせに書くと
、自動的に連結されます:

   >>> 'Py' 'thon'
   'Python'

この機能は長い文字列を複数行に分けて書きたいときに特に便利です:

   >>> text = ('複数の文字列を丸括弧で囲むと'
   ...         '連結される。')
   >>> text
   '複数の文字列を丸括弧で囲むと連結される。'

ただし、この方法で連結できるのはリテラルどうしだけです。 変数や式には
使えません。

   >>> prefix = 'Py'
   >>> prefix 'thon'  # 変数と文字列リテラルは連結できない
     File "<stdin>", line 1
       prefix 'thon'
              ^^^^^^
   SyntaxError: invalid syntax
   >>> ('un' * 3) 'ium'
     File "<stdin>", line 1
       ('un' * 3) 'ium'
                  ^^^^^
   SyntaxError: invalid syntax

変数どうしや変数とリテラルを連結するには "+" を使います:

   >>> prefix + 'thon'
   'Python'

文字列では *インデックス* (添字) を指定して文字を取得できます。最初の
文字のインデックスは 0 です。文字専用の型はなく、1文字も長さ1の文字列
として扱います:

   >>> word = 'Python'
   >>> word[0]  # 0番目の文字
   'P'
   >>> word[5]  # 5番目の文字
   'n'

インデックスに負の数を指定すると、右から数えて文字を取得できます:

   >>> word[-1]  # 最後の文字
   'n'
   >>> word[-2]  # 後ろから2番目の文字
   'o'
   >>> word[-6]
   'P'

-0 は 0 と区別できないので、負のインデックスは -1 から始まります。

インデックス指定に加えて *スライス* も使えます。インデックス指定では個
々の文字を取得し、 *スライス* では部分文字列を取得できます:

   >>> word[0:2]  # 0番目(含む)から2番目(含めない)までの文字
   'Py'
   >>> word[2:5]  #  2番目(含む)から5番目(含めない)までの文字
   'tho'

スライスのインデックスには便利なデフォルト値があります。最初のインデッ
クスを省略すると 0 になり、2つ目を省略すると対象の文字列の長さになりま
す:

   >>> word[:2]   # 最初から2番目(含めない)までの文字
   'Py'
   >>> word[4:]   # 4番目(含む)から最後までの文字
   'on'
   >>> word[-2:]  # 後ろから2番目(含む)から最後までの文字
   'on'

開始位置の文字は常に含まれ、終了位置の文字は常に含まれません。このため
"s[:i] + s[i:]" は常に "s" と等しくなります:

   >>> word[:2] + word[2:]
   'Python'
   >>> word[:4] + word[4:]
   'Python'

スライスの仕組みを覚えるには、インデックスが文字と文字の *間* を指し、
最初の文字の左端を 0 と考えるとよいでしょう。すると、長さ *n* の文字列
では最後の文字の右端のインデックスが *n* になります。例えば次のように
なります:

    +---+---+---+---+---+---+
    | P | y | t | h | o | n |
    +---+---+---+---+---+---+
    0   1   2   3   4   5   6
   -6  -5  -4  -3  -2  -1

数字の1行目は文字列内のインデックス 0 から 6 の位置を示し、2行目は対応
する負のインデックスを示しています。*i* から *j* までのスライスには、
*i* と *j* の印を付けた境界の間にあるすべての文字が含まれます。

両端のインデックスが非負で文字列の範囲内にある場合、スライスの長さは2
つのインデックスの差になります。例えば "word[1:3]" の長さは 2 です。

大き過ぎるインデックスを使おうとするとエラーが発生します:

   >>> word[42]  # 文字列は6文字しかない
   Traceback (most recent call last):
     File "<stdin>", line 1, in <module>
   IndexError: string index out of range

一方、スライスではインデックスが範囲外でもエラーになりません:

   >>> word[4:42]
   'on'
   >>> word[42:]
   ''

Python の文字列は *不変* で、内容を変更できません。そのため、文字列の
インデックスで指定した位置に代入するとエラーになります:

   >>> word[0] = 'J'
   Traceback (most recent call last):
     File "<stdin>", line 1, in <module>
   TypeError: 'str' object does not support item assignment
   >>> word[2:] = 'py'
   Traceback (most recent call last):
     File "<stdin>", line 1, in <module>
   TypeError: 'str' object does not support item assignment

別の文字列が必要な場合は新しく作成します:

   >>> 'J' + word[1:]
   'Jython'
   >>> word[:2] + 'py'
   'Pypy'

組み込み関数 "len()" は文字列の長さを返します:

   >>> s = 'supercalifragilisticexpialidocious'
   >>> len(s)
   34

参考:

  テキストシーケンス型 --- str
     文字列は *シーケンス型* の一種で、シーケンス型に共通する操作を使
     えます。

  文字列メソッド
     文字列には基本的な変換や検索を行うためのメソッドが数多くあります
     。

  f-strings
     式の埋め込みをサポートした文字列リテラル

  書式文字列の構文
     "str.format()" を使った文字列のフォーマットについて説明しています
     。

  printf 形式の文字列書式化
     文字列を "%" 演算子の左オペランドに指定して行う従来のフォーマット
     操作について、詳しく説明しています。


3.1.3. リスト型 (list)
----------------------

Pythonは多くの *複合 (compound)* データ型を備えており、複数の値をまと
めるのに使われます。最も汎用性が高いのは *リスト (list)* で、コンマ区
切りの値 (要素) の並びを角括弧で囲んだものとして書き表されます。リスト
は異なる型の要素を含むこともありますが、通常は同じ型の要素のみを持ちま
す。

   >>> squares = [1, 4, 9, 16, 25]
   >>> squares
   [1, 4, 9, 16, 25]

文字列 (や他の全ての組み込みの *シーケンス* 型) のように、リストはイン
デックスやスライスができます:

   >>> squares[0]  # インデックス指定は要素を返す
   1
   >>> squares[-1]
   25
   >>> squares[-3:]  # スライスは新しいリストを返す
   [9, 16, 25]

リストは、リストの連結などもサポートしています:

   >>> squares + [36, 49, 64, 81, 100]
   [1, 4, 9, 16, 25, 36, 49, 64, 81, 100]

*不変* な文字列とは違って、リストは *可変* 型ですので、内容を変更でき
ます:

   >>> cubes = [1, 8, 27, 65, 125]  # 何かがおかしい
   >>> 4 ** 3  # 4の3乗は65ではなく64!
   64
   >>> cubes[3] = 64  # 誤った値を置き換える
   >>> cubes
   [1, 8, 27, 64, 125]

"list.append()" *メソッド* を使って、リストの末尾に新しい要素を追加で
きます (メソッドについては後で詳しく見ていきます):

   >>> cubes.append(216)  # 6の3乗を追加
   >>> cubes.append(7 ** 3)  # 7の3乗を追加
   >>> cubes
   [1, 8, 27, 64, 125, 216, 343]

単純な代入ではPythonは決してデータをコピーしません。リストを変数に代入
すると、その変数は *既存のリスト* を参照します。ある変数を通してリスト
に任意の変更を行うと、同じリストを参照している他のすべての変数からもそ
の変更を確認できます。:

   >>> rgb = ["Red", "Green", "Blue"]
   >>> rgba = rgb
   >>> id(rgb) == id(rgba)  # 同じオブジェクトを参照している
   True
   >>> rgba.append("Alph")
   >>> rgb
   ["Red", "Green", "Blue", "Alph"]

全てのスライス操作は、指定された要素を含む新しいリストを返します。例え
ば、次のスライスは、リストの 浅いコピー を返します。:

   >>> correct_rgba = rgba[:]
   >>> correct_rgba[-1] = "Alpha"
   >>> correct_rgba
   ["Red", "Green", "Blue", "Alpha"]
   >>> rgba
   ["Red", "Green", "Blue", "Alph"]

スライスには、代入もできます。スライスの代入で、リストのサイズを変更し
たり、全てを削除したりもできます:

   >>> letters = ['a', 'b', 'c', 'd', 'e', 'f', 'g']
   >>> letters
   ['a', 'b', 'c', 'd', 'e', 'f', 'g']
   >>> # 一部の値を置き換える
   >>> letters[2:5] = ['C', 'D', 'E']
   >>> letters
   ['a', 'b', 'C', 'D', 'E', 'f', 'g']
   >>> # 一部の値を削除する
   >>> letters[2:5] = []
   >>> letters
   ['a', 'b', 'f', 'g']
   >>> # 要素全体を空のリストに置き換えてリストをクリアする
   >>> letters[:] = []
   >>> letters
   []

組込み関数 "len()" はリストにも使えます:

   >>> letters = ['a', 'b', 'c', 'd']
   >>> len(letters)
   4

リストを入れ子 (ほかのリストを含むリストを造る) にできます。例えば:

   >>> a = ['a', 'b', 'c']
   >>> n = [1, 2, 3]
   >>> x = [a, n]
   >>> x
   [['a', 'b', 'c'], [1, 2, 3]]
   >>> x[0]
   ['a', 'b', 'c']
   >>> x[0][1]
   'b'


3.2. プログラミングへの第一歩
=============================

もちろん、2 たす 2 よりももっと複雑な課題にも Python を使えます。 例え
ば、フィボナッチ数列 の先頭の部分列は次のように書けます:

   >>> # フィボナッチ数列:
   >>> # 2つの要素の和で次の値を定義する
   >>> a, b = 0, 1
   >>> while a < 10:
   ...     print(a)
   ...     a, b = b, a+b
   ...
   0
   1
   1
   2
   3
   5
   8

上の例では、いくつか新しい機能を使用しています。

* 最初の行には *複数同時の代入 (multiple assignment)* が入っています:
  変数 "a" と "b" は、それぞれ同時に新しい値 0 と 1 になっています。こ
  の代入は、最後の行でも使われています。代入文では、まず右辺の式がすべ
  て評価され、次に代入が行われます。右辺の式は、左から右へと順番に評価
  されます。

* "while" は、条件 (ここでは "a < 10") が真である限り実行を繰り返し (
  ループし) ます。Python では、C 言語と同様に、ゼロでない整数値は真と
  なり、ゼロは偽です。条件式には、文字列値やリスト値なども使えます。そ
  れ以外のシーケンスも、条件式として使用できます。長さが 1 以上のシー
  ケンスは真で、空のシーケンスは偽になります。サンプルで使われている条
  件テストはシンプルな比較です。標準的な比較演算子は C 言語と同様です:
  すなわち、 "<" (より小さい)、 ">" (より大きい)、 "==" (等しい)、
  "<=" (より小さいか等しい)、 ">=" (より大きいか等しい)、および "!=" (
  等しくない)、です。

* ループの *本体 (body)* は、 *インデント (indent, 字下げ)*  されてい
  ます: インデントは Python において、文をグループにまとめる方法です。
  対話的プロンプトでは、インデントされた各行を入力するにはタブや (複数
  個の) スペースを使わなければなりません。実用的には、もっと複雑な処理
  を入力する場合はテキストエディタを使うことになるでしょう。 ほとんど
  のテキストエディタは、自動インデント機能を持っています。複合文を対話
  的に入力するときには、入力完了のしるしとして最後に空行を入力します。
  パーザには最後の行の入力が終わったかどうかを判断できないためです。基
  本的なブロック内では、全ての行は同じだけインデントされていなければな
  らないので注意してください。

* "print()" 関数は、与えられた引数の値を書き出します。これは (前に電卓
  の例でやったような) 単に出力したい式を書くのとは、複数の引数や浮動小
  数点量や文字列に対する扱い方が違います。 "print()" 関数では、文字列
  は引用符無しで出力され、要素の間に空白が挿入されて、このように出力の
  書式が整えられます:

     >>> i = 256*256
     >>> print('The value of i is', i)
     The value of i is 65536

  キーワード引数 *end* を使うと、出力の末尾に改行文字を出力しないよう
  にしたり、別の文字列を末尾に出力したりできます:

     >>> a, b = 0, 1
     >>> while a < 1000:
     ...     print(a, end=',')
     ...     a, b = b, a+b
     ...
     0,1,1,2,3,5,8,13,21,34,55,89,144,233,377,610,987,

-[ 脚注 ]-

[1] "**" は "-" より優先順位が高いので、"-3**2" は "-(3**2)" と解釈さ
    れ、計算結果は "-9" になります。これを避けて "9" を得たければ、
    "(-3)**2" と書きます。

[2] 他の言語と違って、"\n" のような特殊文字は、単引用符 ("'...'") と二
    重引用符 (""..."") で同じ意味を持ちます。両者の唯一の違いは、単引
    用符で囲われた箇所では """ をエスケープする必要がない (ただし "\'"
    はエスケープする必要がある) ことで、逆もまた同様です。
