10 Python Tips and Tricks For Writing Better Codeの内容を軽く日本語でまとめました。
英語のヒアリング未熟なので、もしかしたら間違っている所があるかもしれません。
1) Ternary Conditionals:条件式
ternary operatorsとも呼ぶらしい。
condition = True
if condition:
x = 1
else:
x = 0
print(x)
Trueなら1を、Falseなら0を返すコードです。
このコードのif
文を1行で書くと、
x = 1 if condition else 0
このように、コードをシンプルかつ分かりやすく書ける方法がないか考えることが大事です。
2) Underscore Placeholders:アンダースコアで強調させる
大きい数字が出てきたら、アンダースコア(_
)で強調すると分かりやすくなります。
num1 = 10000000000 # 分かりにくい
num2 = 10_000_000_000 # 分かりやすい
print(f'{num2:,}')
# 10,000,000,000
桁数3つごとで区切って数字を分かりやすくできる。
また、printで出力する時に工夫すれば、より分かりやすくなる。
3) Context Managers:コンテキストマネージャ
コンテキストマネージャとは、
with文の実行時に、runtime context を定義するオブジェクトのことです。
*runtime context とは
__enter__()
呼び出しで組み立てられて、__exit__()
呼び出しで取り壊される環境のこと。
コンテキストマネージャは必ず、特殊メソッドの__enter__()
と__exit__()
を定義しないといけないらしい。
実装例 👇
f = open('test.txt','r')
file_contents = f.read()
f.close()
words = file_contents.split(' ')
word_count = len(words)
print(word_count)
上のコードの最初の3行について、with文でコンテキストマネージャを呼び出すと、
with open('test.txt','r') as f:
file_contents = f.read()
かなり短くなる。
- 少ないコードで可読性増す (特に例外処理の部分で高い効果を発揮する)
- 前処理(
__enter__
)と、後処理(__exit__
)を強制する
といったメリットがあります。
4) Enumerate : enumerate関数
names = ['Mirai','Tech','Denshi']
index = 0
for name in names:
print(index,name)
index += 1
よく見かけるこのようなコード。
enumerate
関数を使えば、for
文がとてもシンプルになります。
for index, name in enumerate(names,start=1):
print(index, name)
5) Zip : zip関数
[ヒーロー]と、[ヒーローの名前]をリストにして表示させたいとします。
先程のenumerate
関数を使って書いてみます。
names = ['Peter Parker','Clark Kent','Bruce Wayne']
heros = ['Spiderman','Superman','Batman']
for index, name in enumerate(names):
hero = heros[index]
print(f'{name} is actually {hero}')
実は、for文の中身で、zip
文を使えば、もっと短く書けます。
for name, hero in zip (names, heros):
print(f'{name} is actually {helo}')
このzip
関数はリストが増えるほど、その効果を発揮します。
例えば、先程のリストに、[ヒーローが活躍する世界]を追加する場合は、
names = ['Peter Parker','Clark Kent','Bruce Wayne']
heros = ['Spiderman','Superman','Batman']
universes = ['Marvel','DC','DC']
for name, hero, universe in zip (names, heros, universes):
print(f'{name} is actually {helo} from {universe}')
このように、zip
関数はリストなどを簡単にまとめられます。
名前はzipファイルから来ているのでしょうか?
6) Unpacking : アンパック
アンパックとは、タプルやリストの要素を展開して複数の変数に代入することです。
様々な要素の取り出し方ができるので便利です。
アンパックの基本
# Normal
items = (1,2)
print(items)
# (1,2)
# unpaccking
a, b = (1, 2)
print(a)
print(b)
# 1
# 2
# Error!
a, b, c = (1, 2, 3, 4)
print(a)
# ValueError:too many values to unpack
変数の数と要素の数は一致する必要があります。
アンダースコア(_
)を使ったアンパック
pythonでは、必要ない値を、_
に代入します。
a, _ = (1,2)
print(a)
print(_)
# 1
# 2
*
を使ったアンパック
*を使えば、要素をリストとしてまとめてくれます。
x = (0, 1, 2, 3, 4)
a, b, *c = x
print(a)
print(b)
print(c)
# 0
# 1
# [2, 3, 4]
a, b*, c = x
print(a)
print(b)
print(c)
# 0
# [1, 2, 3]
# 4
こちらでもっと詳しく解説しています。
7) Setattr/Getattr : 属性の操作を分かりやすく
この関数を使えば、明示的に属性を操作でき、どんな風に設定したか分かりやすくなります。
それぞれ、「Set attribute」 「Get attribute」 の略でしょうか?
class Person():
pass
person = Person()
first_key = 'first'
first_val = 'Bun'
# setattrを使わない場合
person.first_key = first_val
print(person.first)
# setattrを使う場合
setattr(person, first_key, first_val)
#setattr(オブジェクト,属性名,属性値)
first = getattr(person, first_key)
print(first)
# Bun
上記コードのsetattr
では、person
オブジェクトの属性first_key
(ここではfirst)に値first_val
(ここではBun)を設定しています。
そして、getattr
で、オブジェクトと属性を取得しています。
ややこしいことをしているように思いますが、どんな操作をしたのか分かりやすく、属性が増えれば増えるほど効果を発揮します。
属性が増えた時は、辞書を絡めると分かりやすくなります。
class Person():
pass
person = Person()
person_info = {'first':'Bun', 'last':'Tarou'}
for key, value in person_info.items():
setattr(person, key, value)
for key in person_info.keys():
print(getattr(person, key))
# Bun
# Tarou
8) GetPass : パスワード保護
getpass
を使えば、入力したパスワードを隠すことができます。
ユーザーに名前とパスワードを入力させたいとします。
username = input('Yourname: ')
password = getpass('Password: ')
print('Logging in...')
このままだと、入力する時にパスワードが丸見えになり、横からチラ見されたらやばいです。
これを防ぐために、👇のようにします。
from getpass import getpass
username = input('Yourname: ')
password = getpass('Password: ')
repassword = getPass('Again: ')
print('Logging in...')