Photo by francois schnell
秋山です。
Pythonって多少プログラミング経験がある人であれば、文法的にはそこまで難しい言語ではないと思うのですが、初心者の人がPythonでゼロから何か作ろうとしたり、細かい修正をしなきゃならなくなったりしたときに、知っていると得するかもしれないTips的なことを紹介したいと思います。
「既にPython使いまくってる」という人にとってはおなじみの内容ばかりかもしれませんが、「最近Python使い始めた」という人は意外とまだ知らない、そして知っておくとお得なことがある(かもしれない)話です。
■クラスなどの扱いに関して
※他の言語の仕様を全て認識しているわけではないので、Python以外の言語でも似た仕様のものはあるかもしれません。
◆classを定義する際のインスタンス変数、クラス変数のprivate的な動きについて
大多数の言語において、外部から直接アクセスして欲しくない(アクセスできるのはメソッド経由な場合のみに制限したい)変数のために、private修飾子というものがあります。が、Pythonには修飾子としてのprivateは存在しません。
Pythonでは↓このようにアンダーバーを頭に2つつけ、" self.__hoge "というふうに書くことで、ネームマングリング(名前修飾)されたプライベート変数的な扱いとなります。
Paizaというクラスで " self.__piyo "というクラス変数を定義した場合、" paiza = Paiza() " として " paiza.__piyo " では外部からアクセス不可能になります。
また推奨されてはいませんが、" paiza._Paiza__piyo " とすればアクセスすることが可能になります。
■リスト内包表記
◆リストを作るとき
※Python特有(と言いつつHaskellにもあるので他にもあるかもしれない)っぽい表現について
リストを作る際に、 " [i for i in range(1, 10) if i%2 == 0] " という書き方をすると、1から10の偶数を出力できます。これによって、普通はループを使ってリストを生成するような流れの場合もかなりコードを短縮できます。
↓実際に偶数を作り、その偶数リスト全体を2乗したリストを作るコードを書いてみました。
range(1,10) の部分はリストもしくはイテレーターなら何でもいいので、フィルタリングや特定の処理を全てにしたい場合などはすごく重宝します。
慣れないうちは読みづらく感じるかもしれませんが、慣れてくるとさっと書けて、他の言語でmap, filterに当たる記述をまとめて書けるのがよいです。(Pythonにもmapやfilterはありますが)
※たまにリスト内包表記芸みたいな感じで、リスト内包表記で素数を作ったりFizz Buzzしたりするお遊びみたいなコードを見かけますが……それは普通にループ書いた方がよいですよというマジレスを置いときます。Fizz Buzzはこんな感じ↓
またリスト内包表記以外にも、辞書内包表記 " {i : k for i, k in [(i, i**2) for i in range(1, 10)]} " とかすることもできます。
プログラミング経験がある方は、「ここからさらに " (i for i in range(3)) " のようなタプル内包表記などもできるのかしら?」と思うかもしれませんが、この場合はジェネレータ式と呼ばれる別物になります。なのでタプルを作りたい場合はリスト内包表記を記述して、tuple()を使い変換してください。
ジェネレータ式についてはこちらに詳しく書かれています。
関数型プログラミング HOWTO — Python 3.8.0 ドキュメント
■多次元リスト(配列)の作り方
これはですね、地味なハマりどころです。
Pythonで空の特定の長さの0で初期化されたリストを作るとき " a = [0] * 3 " とすることができます。ですので、リストについて少し知っている方は、ここから発展して、 " a = [[0] * 3] * 3 " とかして3×3の0で初期化されたリストを作りたい!と思われるかもしれません。
しかし、これをすると " a[0][0] = 1 " という望まない結果となってしまいます。
a[0][0], a[0][1], a[0][2] がすべて 1 となってしまうわけですが、これはなぜかというと、リストの乗算はコピーではなくオブジェクトへの参照を作ってしまうからなのです。
この場合、初期化されたリストを作りたいなら、推奨される書き方はリスト内包表記を使って " [[0]*3 for i in range(3)] " となります。
また過去のPythonライブラリ記事(後でリンク貼ります)で紹介したNumPyなどを使うと、
numpy.zeros((3, 3))
と書くことで作れます。((3, 3)の部分は引数ではなくタプルである点に要注意です。(3, 3, 3)と与えれば3次元配列を作ってくれます)
■三項演算子
三項演算子は、一般的な言語では " bool ? a : b " という記法が一般的です。最初に条件式、左側がTrue,右側がFalseという感じですね。
これがPythonの場合は、" a if bool else b " という書き方になります。中央に条件があり左側がTrue, 右側がFalseの場合の値という順になっているので、他の言語での三項演算子に慣れていると、違和感があるかと思います。
■まとめ
Python始めたばっかり…っていうかプログラミングも始めたばっかり! という人にはちょっと「???」な内容もあったかもしれませんが、いつか他の人が書いたコードを読んだり修正したりすることになったときに、こういった書き方のコードが出てきたら思い出してください。
また、こうした便利な書き方を適宜利用することで、冗長じゃなく簡潔で読みやすいPythonコードを書いていっていただければと思います。
paizaでもPythonが学べる動画学習コースを無料で公開しています。ちょうど本日「Python入門編4」の動画が公開になったところですので、「Pythonに興味あるけどプログラミング初心者です!」という人はぜひのぞいてみてください。
あと途中でブログパーツとして使ったオンライン実行環境サービス「paiza.IO (パイザ・アイオー)」はこちら。
私は前回、前々回の記事もPythonについて書いてますので、ご興味ある方はごらんください。
paiza.hatenablog.com
paizaは、技術を追い続けることが仕事につながり、スキルのある人がきちんと評価される場を作ることで、日本のITエンジニアの地位向上を目指したいと考えています。
自分のスキルを磨いていきたいと考えている方におすすめなのが「paizaラーニング」。オンラインでプログラミングしながらスキルアップできる入門学習コンテンツです。初心者でも楽しくプログラミングの基本を学ぶことができます。
そして、paizaでは、Webサービス開発企業などで求められるコーディング力や、テストケースを想定する力などが問われるプログラミングスキルチェック問題も提供しています。
スキルチェックに挑戦した人は、その結果によってS・A・B・C・D・Eの6段階のランクを取得できます。必要なスキルランクを取得すれば、書類選考なしで企業の求人に応募することも可能です。「自分のプログラミングスキルを客観的に知りたい」「スキルを使って転職したい」という方は、ぜひチャレンジしてみてください。