Scrapboxを使って技術書の輪読会を進めた話

 

この記事は何?

  • Scrapbox」という、情報共有用のノートを複数人で同時編集できるツール(Googleドキュメントに近いサービスですね)を用いて、自然言語処理の勉強会を完走したので、その進め方について紹介します。

  • 輪読会をやりたいけど、どうやって進めるのが良いのかな?と悩まれている方の参考になれば幸いです。今回はコロナ禍もあってオンラインで開催していましたが、オフラインの勉強会であっても同じやり方が適用できると思います!
    また、自然言語処理以外の輪読会を開く場合にも同様に進められるはずです。

  • 一緒に勉強会を完走してくださった下記の仲間にこの場を借りて感謝申し上げます、ありがとうございました!

    asteriam (@asteriam_fp) | Twitter

    しんちろ (@sinchir0) | Twitter


    takapy | たかぱい (@takapy0210) | Twitter

サンプルについて

下でつらつら説明する前に、まずはどんな感じのものを作ったのか、ざっと見ていただければと思います!

scrapbox.io

理想的には、実際に使ったノートをそのまま公開したかったのですが、テキストからの引用についても多く行っていたため、著作権に抵触する箇所を削除したものを貼っています。

それでは、輪読会の進め方について以下で説明していきます。

進め方について

事前準備

  1. 次回までの範囲について、各々が読んでいくなかで「わかったこと」「分からなかったこと、質問したいこと」「納得できないこと」などを箇条書きでScrapboxに記入していく。この時、他の人が書いていることに対してもどんどん追加コメントをしていきます。(同意・回答・補足など。)

    今回の場合は、範囲を1章ごとに区切って進め、インターバルについては次回の内容の濃さ次第で1週間または2週間のどちらかを選択しました(※簡単な章が続く場合は、複数の章をまとめて1回に詰め込みました)。教材は「機械学習・深層学習による自然言語処理入門 scikit-learnとTensorFlowを使った実践プログラミング」を使いました。

輪読会当日

  1. 決めた時間にGoogle Meetsに集合し、書かれた内容について上からみんなで読んで確認していく。疑問が残っている内容についてみんなで議論する。その場での口頭による追加質問も大歓迎。

  2. 1.で解決できず、かつ調べた方が良さそうなことは各自の宿題とする。

  3. 次回の章の範囲と集合時間を決め、解散。「事前準備編」に戻る。

以上のループを繰り返し。

やってよかったこと

  1. 質問するハードルを限りなく下げる
    「〜ってなんでしたっけ?」という簡単な復習のような質問も気軽に書いていくことで、他のメンバーも結果的に「言われてみればあんまりちゃんと分かってないな」と気づかされることも多かったです。今回は既に顔馴染みのあるメンバーだったので発言はしやすかったと思いますが、初めましての人たちとやるときは別途アイスブレイクの時間などもあると良いのかなと思いました。
    また、「変なこと聞いちゃってすみません」などという発言に対しても「そんなことないです」とフォローし合う空気づくりも大切だと思いました。優しいメンバーに恵まれたおかげで、この点はあまり困らなかったというか、自然にそういう空気感が醸成できていたと思います。

  2. 1.に関連しますが、多少本の大枠と外れたことであってもどんどん質問・コメントし合うようにしました。
    例えば、コードの書き方やフォーマッティングに関する良い/悪いプラクティスは何なのかであったり、環境構築のTipsといった事柄にも話が及びました。また、今回は自然言語処理を実務に適用することに興味のあるメンバーが揃っていたので、「実際実務で使えるのか?」といった問いも非常に有意義でした。

  3. Scrapboxに疑問をまとめる形式を採用したことで、「全員が毎回の範囲で当事者意識を持って参加できる」という利点が生まれたと思います。
    輪読会でよくあるのが、「持ち回りで1人ずつが本の内容をまとめて発表」という形式だと思いますが、この場合、「自分が担当ではない回はどうしても内容理解などの準備が甘めになってしまう」とか、「質疑はその場限りになっていて、みんなの時間を奪ってまで今挙手して質問を投げかけるのは憚られるので、手を挙げない」などといったデメリットがあります。
    一方、Scrapbox全員参加形式の場合は、「事前に書けば書くほど自分の疑問に答えてもらえる!」というインセンティブが働き、結果として多くの質問が集まりやすくなる仕組みになっていたと思います。

  4. 事前に議論する事柄がScrapboxでチェックできるので、ある程度心と頭の準備がある状態で臨める。
    これも、従来のように発表資料を誰かが準備して〜という形式にすると、直前まで資料にアクセスできないことが多く、その場で初めて議論したい内容について問いかけられ、考え始める(そして中身の濃い議論にならない)ケースが目立つと思います。
    一方、Scrapbox形式であれば、事前に何について話し合うのか分かり、自分なりの意見を考えておけるだけでなく、そのことについて下調べしておくこともできます。結果として、意味のある議論につながりやすかったと思います。

  5. 誰がコメントしたものなのかすぐにわかる。
    これは賛否両論あるかもしれませんが、今回のように誰でもどんなことでも書いて良いというハードルの低い状態を保てている限りは、誰が書いたものか分かった方が、質問の意図をすぐに確認できて便利でした。
    Googleドキュメントを使っていると、「誰がその箇所を編集したのか?」は変更履歴を開かないと見えてきませんが、Scrapboxでは「Command+i」というショートカットで、手軽に本文中に自分のアイコンを載せることができます。この仕組みを使って、誰が何を書いたのかが簡単に可視化できるようになりました。

f:id:taro_masuda:20210531135926p:plain

図:各メンバーのアイコンがScrapbox上に表示されている様子

 

今後やるときに改善したいこと

  1. アドバイザーを1人以上呼びたいと思いました。
    理由は簡単で、メンバーのうち誰もクリアな答えを持っていない疑問については、その場で解決しようがなかったためです。とはいえ、圧倒的に強い人の存在により、質問のハードルも無意識に上がってしまうリスクもあると思うので、場の雰囲気作りには注意が必要そうです。

  2. ファシリテーターを持ち回りにすること。
    特に誰が進行をリードしていくかを決めずに続けていましたが、その場の空気感でしんちろさんにばかり仕切りを任せてしまっていました。次やるときは、回ごとに役を入れ替える形式にすると良いと思いました。

  3. 前回未解決だった宿題についてのチェックが甘めだったかなと思います。
    前回残っていた疑問については、メンバーの誰かが調べてくれた内容をシェアしてくれることもありましたが、ちゃんと振り返ることが習慣として定着していなかったです。次やるときには、各回のアジェンダとしてしっかり盛り込んでおこうと思います。

以上です。輪読会企画の際はぜひ参考にしてみてください!

転職活動中にCodilityでオンラインコーディング選考を受けた話

# この記事は何?

  • 機械学習エンジニア/データサイエンティスト職で転職活動していた増田と申します。今回は、某企業の選考の過程で、Codilityというサイトを使ったオンラインコーディングテストを受ける、という珍しい(?)体験をしたので、体験記を共有します。
  • 選考の具体的な企業名、問題のずばりそのままは公開しません。

# Codilityとは何?

Codilityとは、ブラウザ上で実施するオンラインコーディングテストプラットフォームです。受験の流れは以下になります。

  1. 企業から受験案内のURLが送られてきます。
  2. URLをクリックして「Start」を押すと、ブラウザ上のエディタが立ち上がります。受験者は、制限時間内に問題文の指示通りに動くプログラムを書きます。問題数、制限時間は企業が指定し、受験者は「Start」押下前に問題の数と制限時間を確認できます。
  3. 書き終わったら提出(Submitボタンをクリック)します。

既にオンラインジャッジシステム(AtCoder、AizuOnlineJugdeなど)に慣れ親しんでいる方は、それの就活版だと思ってくださればイメージが付くと思います。ただし、AtCoderといくつか違う点があり、以下にまとめます。

# AtCoderとの違い

  1. 関数のシグネチャが事前に与えられる。つまり、標準入出力でやり取りすることはなく、用意された引数に対して処理を書いていけばOKです。
  2. 問題文は全部英語で、かつ問題文がコピー不可になっており、翻訳機にかけることができません。そこまで難しい単語や表現が出てくる印象はないですが、普段日本語でしか問題を解いたことがない方は、事前に何問か練習しておくと良いでしょう。
  3. Submitは1度きり(※問1つに対して1回ずつだけ押せる、の意)。十分にコードテストを走らせ、ケアレスミスがなさそうな確証を得てからSubmitボタンを押すようにしましょう。
  4. 問題の傾向としては、AtCoderのような数学的考察が必要はあまり必要なく、どちらかというとLeetCodeに載っているような、いわゆるテックジャイアント企業が用いるような王道のアルゴリズム/データ構造に関する問題が多い気がします。練習をするならAtCoderよりもCodilityまたはLeetCodeを使うと良いでしょう。
  5. 受験時間帯:Codilityの場合、受験時間を自由に設定できます。ただし、企業側からは「なるべくN日以内に受けてください」と連絡があるはずなので、最低限そこに遅れないようにしましょう。
  6. 部分点が与えられる:Codilityの最終スコアは「Correctness(small~mediumテストケースを何%合格したか)」と「Performance(largeテストケースに対して、時間以内に終了するか)」の2軸で評価され、AtCoderのように全ケースクリアして初めて加点、というわけではないようです。また、問いの種類によっては、「この問題はPerformanceでは採点しないため、大きな入力は考慮しなくて良い」という断り書きがある場合もあります。
  7. ブラウザ上のエディタがそこそこリッチ:変数名の補完機能が使えたりします。
  8. 提出したソースコードは選考で使われる:仕事で書いているような、第三者が見て分かりやすいコードを書くことをお勧めします。

# AtCoderと同じところ

  1. 試験中はググってOK。
  2. タイマーの一時停止は不可。邪魔されない自信のある時間をきっちり確保しましょう。宅配便の配達なども時間指定で避けておくと良いですね。ちなみに筆者の場合は、昼15時頃に受験していたら途中で廃品回収車の大きな音が近づいてきて集中力を欠いてしまいました。夜に受ければよかったです😭
  3. (もちろん)替え玉受験や友達との共同作業は不可。原理的に替え玉は見抜けませんが、倫理的に著しくアウトなのでやめましょう。

# どんな問題が出たの?

CodilityでいうところのPainless〜Respectable、LeetCodeでいうところのEasyレベルだと思います。同じくらいの難易度(当社比)の問題だとこの辺りでしょうか。

AtCoderレートでいうと茶色までの人はちゃんと練習が必要そう、緑の人はちょっと形式慣れしておけばまあ行けそう、水色以上の人はお茶の子さいさいといったところでしょうか。ここも恐らく、企業によって難易度の調整が変わるところだと思います。

# 受験結果

  • 選考で次のプロセスに進めたので、結果的には成功したようです。
  • ある問題で大きく点を落としてしまいました。後でググってみたところ、それは界隈ではちょっと有名な問題を軽くひねったものだったようです。不合格を覚悟しましたが通過できたので、単なる正解率だけでなく、コードの書き方も加味してくれたのかもしれません。実際、コードの readability はかなり意識して書くようにしました。

# 終わりに

  • この記事ではCodilityを使ったオンラインコーディング選考を受けた体験記をまとめました。
  • 同じ立場になった(あるいは将来なる)方に対して少しでもお役に立てていたら嬉しいです。

kaggle docker-pythonとGCPによる環境構築で無限にハマりポイントがあったので列挙する

この記事は何?

タイトルの通り、kaggle docker-pythonのイメージを用いてGCPインスタンスで環境構築したい方向けに、自分がハマった注意点を箇条書きにしたものです。この記事を見て、環境構築に苦しむ1人でも多くの方のお役に立てれば幸いです。

注意:2020年8月頃の検証で分かった事実を列挙しているため、現在の仕様と食い違っている箇所がある場合があります。あらかじめご承知おきください。

ブートディスクの容量について

- デフォルトだと10GBになっていますが、kaggleのdocker image自体だけで18GBあるのと、コンペのデータセットやら学習した重みの保存やらを合わせると500GBくらいは確保しておいた方が安全なのではないでしょうか。後から「No space left on disk」系のエラーで怒られて新たにVMインスタンスを作成し直すのも時間と手間がかかる操作なので、始めから余裕を持った容量を選択しておきましょう。

Linux OSイメージの選択について

- CentOS8が個人的なお勧めです。他にも後述するOSもいろいろ試したのですが、全て行き詰まってしまいインスタンスの作り直しを何度もする羽目になってしまいました。ちなみに、GPU付きインスタンスを2つ以上立てるのはGCPから拒否されることが多いようなので、削除→作り直しという面倒なステップを毎回踏むことになります…

上手くいかなかったOSとその理由

- Container-Optimizes OS (COS)

    - 下記のURLの通りCUDAのドライバーをインストールしようとしたところ、「cos-extensions: command not found」になってしまい、先に進めなかった。

https://cloud.google.com/container-optimized-os/docs/how-to/run-gpus

 

他にも、「Ubuntu 18.04 LTS」「Red Hat Enterprise Linux (RHEL) 7」「Deep Learning on Linux」などを試しましたがCUDA周りのインストール作業でつまづいてしまった記憶があります(メモを詳細に取っていませんでした。。。また時間があれば再検証したい)。

その他

- Kaggle docker pythonGPU版をrunするとき、URLに書いてある--runtime nvidiaはdeprecatedな書き方のようです。代わりに--gpus allを指定すると動きました。

- kaggle-pythonイメージのビルド中に「CondaHTTPError: HTTP 503 SERVICE UNAVAILABLE: BACK-END SERVER IS AT CAPACITY」というエラーが出る現象がありました。読んで字の如くで、この時はAnacondaのサーバーが数時間単位で落ちており、ビルドコマンドを繰り返してもどうしようもない状況でした。解決策としては諦めて寝る/明日やり直す、くらいしかないだろうと思います。。。

- 普通のシャットダウンのノリでdockerコンテナ内で exit コマンドを叩くと、せっかく作ったコンテナが消滅するという恐ろしいことになります。。。コンテナから抜ける時はCtrl+p -> Ctrl+qで起動したまま抜けるという癖をつけることをお勧めします。

バンダイナムコ音声コンペ 16th place solution と参加体験記

こんにちは、公私問わず機械学習技術に触れる日々を送っているエンジニアの増田といいます。初めてブログを書いてみます。

初投稿記事として、バンダイナムコさんが主催されていた音声のノイズ除去コンペにて16位(上位4%)に入賞できた体験について、そのsolutionの共有と参加してみての所感を綴っていこうと思います。

f:id:taro_masuda:20200529010222j:plain

終結果としてのリーダーボードに筆者名前とベストスコアが載った様子

- コンペの紹介ページ: https://athletix.run/challenges/czaMEOxQG

コンペの概要

タスク:ノイズが付加された単一人物による発話音声のメルスペクトログラムが30ファイル(1ファイルあたり数秒程度)、および同一人物によるノイズの無い発話音声のメルスペクトログラムが100ファイル(同じく1ファイル当たり数秒程度)与えられます。ノイズの付加された30個のメルスペクトログラムそれぞれについて、ノイズを除去したメルスペクトログラムを求めてください。

評価指標:正解メルスペクトログラムとのMSE(Mean Squared Error)の30ファイル分の平均値

このコンペのユニークな点は2つあります。

① ノイズあり音声とノイズ無し音声の発話内容は異なるため、同一の発話のペア(パラレルデータ)がない。よって、単純な教師あり学習(正解として出力が近づくべき教師データが直接使える)とはならない

② ノイズあり・ノイズ無し音声の発話者は同一(1名のみ)。

16th place solution

ソースコードは以下のリンクにて公開しています。結果として何の変哲もないローパスフィルタをかける、という信号処理ベースの手法がベストスコア(MSE: 2.47)となりました。

https://github.com/taro-masuda/bandainamco_speech_denoising/blob/master/lowpass.ipynb

正直なところ、この手法は手始めにsubmitの操作の流れを掴むための第一歩として試したノリだったので、最終的にこれがベストスコアになるとは何とも複雑な気分でした。というのも、他にも以下の3つの手法など、より趣向を凝らした手法をいろいろ試してみましたが、上記のシンプルな手法に勝る結果は得られなかったためです。

- ノイズの無いデータにランダムノイズを付与したスペクトログラムを入力とし、Autoencoder(自己符号化器)を学習させて、ノイズの無い音声を復元するようなニューラルネットワークを構築する手法(MSE: 7.06)

→ 中間層の数などいわゆるハイパラ調整にもっと時間が割けていればスコアが改善したかもしれません。上位の方のsolutionにも使われていたので、もう少し試行錯誤してみる余地があると思います。

- NMF (Nonnegative Matrix Factorization, 非負値行列因子分解) を用いてノイズの無いスペクトログラムの行列を音声のスペクトル基底とアクティベーションに分解し、ノイズの無いスペクトル基底を得る。次に、ノイズのあるスペクトログラムの行列分解結果の一部を、ノイズの無いスペクトル基底に置換しながら行列分解の最適化のiterationを回していく手法(MSE: 12.53)

→ 試した手法の中で最も誤差が大きくなりました。原因として、ノイズの無いスペクトル基底を無理やり使うという発想では、十分にノイズのあるスペクトログラムを近似できなかったのだと考えられます。実際に復元してみた音声を耳で聴いてみても、他の手法よりもノイズが目立っていました。

- スペクトログラムを2次元の画像とみなし、まずノイズの無い音声から細かく切り取った正方行列(4x4、8x8など)のパッチを多数用意する。次にノイズのあるスペクトログラムの細かい正方領域について全パッチとのユークリッド距離を算出し、最も距離の小さいパッチでノイズのあるスペクトログラムを貼り替える、という手法(MSE: 3.39)。上記のユニークな点②に挙げたように、事前に同一話者のノイズのないメルスペクトログラムが与えられているので、それらを切り貼りして繋ぎ合わせた結果としてのスペクトログラムも、同様にノイズの少ないメルスペクトログラムとして得られるはずだという発想です。

 → 4x4, 8x8, 16x16などのパッチを用いた結果、4x4で最もスコアが高くなりました。しかし、ノイズありの音声との単純なユークリッド距離という発想ではスコア改善の限界があろうことも同時に手ごたえとして実感しました。

体験記

良かった点

- Submit数に制限が無かったこと。こちらはともすれば正解をハックするなど悪用されかねないルールであるとも言えますが、コンペの特性上手元でValidationができなかったので、気軽にSubmitのスコアが確認できたのはとてもありがたかったです。

- データセットのサイズが大きすぎず、1つの手法で試行錯誤する時間が大規模データセットを使う場合と比べて短かったこと。コンペの開催期間が限られているなかでいろいろ試せる仕組みになっていたのはありがたかったです。

- コンペ終了後に正解データとスコア算出スクリプトが公開されたこと。コンペのページ自体は閉じてしまいましたが、これらによりlate submissionの代わりとして復習に使える役者が整ったことになります。上述した手法に対する正確なスコアも、これがあって初めて把握できました。

- KaggleによくあるFinal subを選ぶ形とは異なり、自分が今まで提出した中でのベストスコアが最終結果に自動反映されること。後述の通り自分のスコアは大雑把にしか把握できない仕組みになっていたので、この自動反映は助かりました。

気になった点

- 途中経過のLeaderboardが上位10人までしか表示されなかったため、自分が今どれくらい惜しい位置にいるのか掴めませんでした。次回以降はより詳細なLeaderboardの表示に期待します。

- 自身のsubmitに対するスコア表示がMSEで大雑把なオーダー(10^nのスケールの場合、nのみ)しか開示されず、どのサブミットも同じような表示になり、どの手法がどれくらい有効なのか確認できませんでした。1を切るくらいの有効打が出せたのは上位2名のみだったようなので、ほとんどの参加者はこの仕様に苦しめられたと思います。

- Kaggleにて利用可能なDiscussionチャネルやノートブックの公開などが存在しませんでした。コンペ進行中にも参加者同士で議論しながら進められたら全体としてのレベル感ももう少し上がったのではないかなと思いました。

自身の反省点

もっと早くコンペに取り組み始めればよかった。本コンペは期間が丸々1ヶ月与えられていたのに、競プロなど別の勉強にうつつを抜かしていた結果、初サブミットを果たしたのが締め切り5日前という体たらくでした。また、締め切り日が平日金曜日だったため、昼に業務をして夜~深夜にコンペに取り組むという高負荷稼働を連日続けた結果最終日に風邪を引き寝込む(会社も休む)という最悪のラストスパートとなってしまいました。皆様も無理のないコンペライフを送れるようご自愛くださいませ。

さいごに

音を扱うコンペは、テーブル・画像・自然言語と比べてとても珍しく、自分にとって興味深く取り組めたコンペでした。このような機会を下さり、またソリューションの公開に許諾を下さった株式会社バンダイナムコ研究所のご担当者様方に感謝いたします。