「マンガでやさしくわかる会社の数字」は初心者には分かりやすかった。
「会社」というものについて最近興味が湧いてきたので、簡単にざっと知れそうな本を読みました。
本の題名は、「マンガでやさしくわかる会社の数字」です。
この「マンガでやさしくわかる」シリーズは大変気に入っています。 ストーリー形式で内容に飽きにくいですし、解説の部分もイラストが多くて理解の助けになります。
内容
キーワードとしては以下のようなものが登場してきました。
原価計算、貸借対照表、損益計算表、キャッシュフロー計算書、在庫管理、ABC分析、手形・小切手、 景気、金利、GDP、日銀短観、物価指数、外国為替、株式、PER、PBR、ROE、 経営分析、売上高利益率、ROA、総回転資本率、流動比率、当座比率、固定比率、自己資本比率、損益分岐点 など
前半では貸借対照表と損益計算表の説明を丁寧にして、途中は割と経済全般の話が入って、後半は経営分析のための指標の説明といった感じでした。
ちなみにマンガのストーリーは、地方のとあるスーパーマーケットの経営を立て直そうというもの。 やや面白かったです。
読書時間
読み終わるまでに要した時間は2時間くらいで、 マンガを読んでいる時間が10分くらいで、残りが解説を読んでいる時間、といった割合でした。
感想
多くの指標が登場しており、初学者が一度に全部覚えるのはなかなかの大変なのですが、 それぞれの説明は優しく具体的なので、何度か読み返してもいいかなと思えました。
全体を通して浅い説明といった感じでした。
「会社」というものに興味を持ち始めたのなら、最初に手に取る本として良いと思います。
- 作者: 前田信弘,葛城かえで,たかみね駆
- 出版社/メーカー: 日本能率協会マネジメントセンター
- 発売日: 2016/11/18
- メディア: Kindle版
- この商品を含むブログを見る
Pythonでクラス内の複数メソッドに一括でデコレータを当てる。
調べて試して、盛大に時間を使って詰まったので備忘録として残します。 本記事はPython3.6.4を想定しています。
背景
- アプリケーションコード内には多くのクラスが定義されている。
- それぞれのクラスには、またまた多くのメソッドが定義されている。
- それら多くのメソッドの前後に、共通処理を挟みたくなった。
class A: def method1(): .... def method2(): .... ....(メソッドいっぱい) class B: ....(メソッドいっぱい) class C: ....(メソッドいっぱい) ....(クラスいっぱい)
やりたかったこと
- クラスにデコレータを付けることで、一括で複数メソッドにデコレータを当てたい。
- メソッドによってはデコレータを付けたくない。
- 管理の点から、できるだけシンプルに書きたい。
完成メージ
@decorate_cls() class A: def method1(): .... def method2(): .... .... @decorate_cls() class B: .... @decorate_cls() class C: .... ....
やりたくなかったこと
- それぞれのメソッドにひとつずつデコレータを付ける。
結論
- いろいろ試してみた結果、下記のような感じでデコレータを作成できた。
- 登場人物は3つ
- メソッドに当てる引数付きデコレータ:
decorate_fn
- クラスに当てる引数付きデコレータ:
decorate_cls
- デコレータを当てられるクラス:
Test
- メソッドに当てる引数付きデコレータ:
サンプルコード
from functools import wraps import inspect # メソッドに当てる引数付きデコレータ def decorate_fn(name=''): def wrapper(fn): @wraps(fn) def decorate(*args, **kwargs): print(f'----{name} start----') result = fn(*args, **kwargs) print(f'----{name} end----') return result return decorate return wrapper # クラスに当てる引数付きデコレータ def decorate_cls(exclude=[]): def decorate(Cls): for name, fn in inspect.getmembers(Cls): if name.startswith('__'): continue if callable(getattr(Cls, name)) and not name in exclude: setattr(Cls, name, decorate_fn(name)(fn)) return Cls return decorate # デコレータを当てられるクラス @decorate_cls(exclude=['not_decorated']) class Test(): @classmethod def decorated_classmethod(cls): print('This is classmethod.') def decorated_method(self): print('This is decorated method.') def not_decorated(self): print('This is not decorated.') if __name__ == '__main__': Test.decorated_classmethod() test = Test() test.decorated_method() test.not_decorated()
実行結果
----decorated_classmethod start---- This is classmethod. ----decorated_classmethod end---- ----decorated_method start---- This is decorated method. ----decorated_method end---- This is not decorated.
解説
メソッドに当てる引数付きデコレータ
まずは def decorate_fn()
から。
これは、メソッドに当てる引数付きデコレータ。 今回は引数としてメソッド名を受け、メソッドの実行前後に下記のようなprint文を挟んだ。
----<method name> start---- ----<method name> end----
Python3における引数付きデコレータの書き方については、すでに良い記事があるのでそちらを参考にしてほしい。 qiita.com
自分はちゃんとfunctools.wraps
を使っています。
クラスに当てる引数付きデコレータ
次に、def decorate_cls()
とりあえず再掲。
# クラスに当てる引数付きデコレータ def decorate_cls(exclude=[]): def decorate(Cls): for name, fn in inspect.getmembers(Cls): if name.startswith('__'): continue if callable(getattr(Cls, name)) and not name in exclude: setattr(Cls, name, decorate_fn(name)(fn)) return Cls return decorate
中身の関数は、クラスオブジェクトを受けて全メソッドを取得し、特殊メソッドでないメソッドに対して先に定義したdecorate_fn()
を当てて、それをもとのクラスにsetattr()
しています。
分かりにくいところとしてはdecorate_fn(name)(fn)
でしょうか。
decorate_fn()
は引数付きデコレータですので、まずdecorate_fn(name)
までの部分でデコレータに引数だけを与えています。
そして返ってくるデコレータに対して(fn)
でメソッドを渡しています。
また、このデコレータも引数付きデコレータにしたかったので、引数を渡せるように関数の入れ子にしています。
デコレータを当てられるクラス
最後に class Test()
いくつか適当にメソッドを定義しているクラスです。
最後に
晴れてメソッド一括デコレータを作れました。 あとはひたすらクラスにこのデコレータを当てるだけ。