2021/01/06(水)シンキングベースボール
おそらく明日には緊急事態宣言発令ということで、去年のように太らないように意識して過ごしたいところです。去年は暇な時間にパンを焼いて食べまくったのが良くなかったという自覚はあるので、すでにホームベーカリーは封印していますw
西武辻監督「サイン出したくない」理想は選手主体 - プロ野球 : 日刊スポーツ
2017年、2018年あたりは選手が考えようという雰囲気は感じられましたが、最近は来たボールを振っているだけという印象です。そんな野球でよく2019年は優勝できたな。
橋上さんのようにケツを持ってくれる人がいない状況で「シンキングベースボール」とやらがどこまで浸透するかはわかりませんが、チームにとって必要であることは間違いないので、いい方向に進んでくれればいいなとは思います。
2021/01/05(火)記念すべき年に
今年もよろしくお願いします。
西武球団社長「記念すべき2021年が幕を開けた」 - プロ野球 : 日刊スポーツ
開幕カードに観戦に行きたいところではありますが、そのころには果たして状況がどのようになっているか。7日に発令される緊急事態宣言がどこまで続くかはわかりませんが、さすがに現時点で開幕が延期ということにはならないと思っています。ただ、フルに観客を入れるのは難しそうですね。今年もしばらくは12,000人継続ですかね……。
野球が始まらなかったり、観客をまったく入れない状況になれば話は別ですが、今年は去年の2試合よりは多く観戦に行きたいと思っています。自分の名前が彫られた刻印レンガも見たいですしね。
2021/01/04(月)仕事始め
2021年の業務が始まりました。
もうみなさんすっかり忘れてしまっている気もしますが、政府からはもともと1月11日まで休みにして欲しいという呼びかけがありました。弊社は休みにこそしませんでしたが、趣旨を尊重して今週は原則として在宅勤務となっています。ただ、今の状況だと来週以降も在宅勤務は継続ですかね……。
そうなってしまうと、今のiOSプロジェクトはMacを持っている私一人で全部テストする羽目になるので、どうにかならないのか真剣に考えています。ストアに公開するつもりはないけど、アプリを登録してTestFlightでテストアプリを配布するとか?
2021/01/03(日)変わる勇気
働きたくないでござる。
西武辻監督コーチ陣に「嫌われろ指令」意識改革促す - プロ野球 : 日刊スポーツ
小関コーチはまだ1年なので評価は保留するとしても、優秀な信号機の黒田、辻監督と戦って陣容を整えつつある西口、豊田以外のコーチは、全員入れ替えの候補になってしかるべきだと思っています。老後のレクリエーションではないのですから、みなさんそろそろ真剣にやっていただきたい。
また、辻監督自身にも変わる勇気を持っていただいて、甘く野球をやっている32歳にそろそろ見切りをつけていただきたいと思います。
2021/01/02(土)書き初め
2021年最初のプログラムを書きました。100行にも満たないプログラムですが、仕事でやっている言語を離れて好きな言語を使える喜びに満ちた、とても楽しい時間を過ごすことができました。
私は作業時間のトラッキングにToggl Trackを利用しており、各エントリのClientにその時間が消費、投資、浪費のどれに当たるかを指定しています。より厳密には、消費、投資、浪費にぶら下げる形で各Projectを作り、それをエントリに割り当てています。
今日作成したのは、一日の時間の使い方を集計するプログラムです。入力が20210101であれば、2021年1月1日の0時から2日の0時までの24時間を対象に、Clientごとの合計時間を集計します。日をまたいだエントリについては、前日分、翌日分を破棄し、当日24時間の中に入っている部分のみを集計します。
もともとAPIの戻り値にはdurationという作業時間の項目があるのですが、今回は当該エントリの開始時刻から次のエントリの開始時刻までを作業時間としています。アプリの操作やサーバー同期の都合上、どうしても終了→即座に次のエントリ開始というわけには行かず、数秒の空白の時間帯が発生してしまうからです。
from itertools import groupby from datetime import datetime, timedelta, timezone from functools import cache import sys import time import requests API_TOKEN = '<YOUR_API_TOKEN>' END_POINT = 'https://api.track.toggl.com/api/v8/' WAIT = 1 def main(target): target_date = datetime.strptime(target, '%Y%m%d').replace(tzinfo=timezone(timedelta(hours=9), 'JST')) start_date = target_date + timedelta(days=-1) end_date = target_date + timedelta(days=1) params = { "start_date": start_date.isoformat(timespec='seconds'), "end_date": end_date.isoformat(timespec='seconds'), } response = requests.get(END_POINT + 'time_entries', params, auth=(API_TOKEN, 'api_token')).json() entries = list(map( lambda x: { 'pid': x['pid'], 'start': max(datetime.fromisoformat(x['start']), target_date), }, filter(lambda x: datetime.fromisoformat(x['stop']) > target_date, response) )) durations = [( fetch_project(start['pid'])[0], stop['start'] - start['start'] ) for start, stop in zip(entries, entries[1:] + [{'pid': 0, 'start': end_date}])] result = [( k, sum([duration[1] for duration in v], timedelta()) ) for k, v in groupby(sorted(durations, key=lambda x: x[0]), lambda y: y[0])] for k, v in result: print(k, format_timedelta(v)) @cache def fetch_project(pid): time.sleep(WAIT) response = requests.get(END_POINT + 'projects/' + str(pid), auth=(API_TOKEN, 'api_token')).json() return fetch_client(response['data']['cid']), response['data']['name'] @cache def fetch_client(cid): time.sleep(WAIT) response = requests.get(END_POINT + 'clients/' + str(cid), auth=(API_TOKEN, 'api_token')).json() return response['data']['name'] def format_timedelta(td): hours, remainder = divmod(td.seconds, 3600) minutes, seconds = divmod(remainder, 60) return f"{hours:02}:{minutes:02}:{seconds:02}" if __name__ == '__main__': main(sys.argv[1])