WEBVTT

00:00.300 --> 00:02.610
こんにちは､ このチュートリアルにようこそ｡ 

00:02.640 --> 00:12.510
さて､ この2つ目の関数を作って重みを初期化し､ この関数は実際にこれらの重みの最適な学習を得るために使われることになります｡

00:12.990 --> 00:17.130
2つ目の関数は､ weightsと呼ぶことにします｡ 

00:17.990 --> 00:19.490
そして､ その中のスコア｡ 

00:19.730 --> 00:25.920
そして､ 引数としてニューラルネットワークを表すオブジェクトendを取る｡ 

00:25.940 --> 00:26.930
というわけで､ 以上です｡ 

00:26.930 --> 00:28.370
そして､ コロン｡ 

00:28.370 --> 00:32.210
そして､ 今度は関数の中に入って､ 私たちがやりたかったことを定義してみましょう｡ 

00:32.300 --> 00:39.830
つまり､ 私たちがやりたかったのは､ 最適な学習ができるようにニューラルネットワークの重みを初期化することなのです｡

00:39.830 --> 00:43.460
ですから､ これは特に直感的にはわからないでしょう｡ 

00:43.460 --> 00:46.520
これは､ 研究論文や実験に基づいています｡ 

00:46.520 --> 00:54.560
これから重みを今まで見たこともないような特殊な方法で初期化しますが､ 信じてください､ それが学習プロセスを最適化するのです｡

00:54.650 --> 01:00.680
そこで､ なぜこのように重みを初期化するのか､ その詳細には触れずに､ そのまま実装することにします｡

01:00.680 --> 01:09.440
そこで､ まず､ 後で使うことになるトリックを使って､ 畳み込みと完全な接続を区別することにします｡

01:09.440 --> 01:14.390
なぜなら､ 私たちの目には目がありますから､ 畳み込み層もあれば､

01:14.390 --> 01:23.450
もちろん完全連結層もあり､ これら2種類の連結の重みの初期化が異なることを思い出してください｡

01:23.540 --> 01:28.640
そこで､ このトリックを使ってこれら2種類の接続を分離し､ いくつかのif条件を使って､

01:28.640 --> 01:33.650
それぞれの接続に対して異なる初期化を行うことにします｡

01:33.950 --> 01:42.620
つまり､ このトリックは､ クラス名と呼ぶ新しい変数を作成し､ それをMオブジェクトと等しくすることです｡

01:42.620 --> 01:45.740
つまり､ Mはニューラルネットワークを表しているのですが､ オブジェクトなんですね｡ 

01:45.740 --> 01:52.190
このオブジェクトから特別な属性を取得します｡ クラス名にダブルアンダーコア､

01:52.190 --> 02:02.960
最初のクラスにダブルアンダーコアドット､ 再び名前にダブルアンダーコア､ そしてもう少しでスコアにもう一つダブルが入ります｡

02:03.080 --> 02:09.500
このように､ 新しいネットワーク・オブジェクトの接続の種類を探すのは､ かなり不格好なトリックです｡ 

02:09.500 --> 02:11.960
でも､ それで私たちが欲しいものを手に入れることができるのです｡ 

02:11.990 --> 02:15.260
if条件を開始すると､ それが意味を持つことが分かると思います｡ 

02:15.260 --> 02:19.430
ちなみに､ ifの条件といえば､ 今すぐにでも始められますよ｡ 

02:19.430 --> 02:26.060
そして､ これから行うのは､ 最初のif条件を開始し､ 最初のケースを取得することです｡ 

02:26.060 --> 02:29.150
それは､ 接続がコンボリューションである場合です｡ 

02:29.330 --> 02:33.380
それで､ この条件を書くために､ ifクラス名を書きます｡ 

02:34.370 --> 02:35.440
でも大丈夫｡ 

02:35.450 --> 02:45.560
ここでは､ findという細かいメソッドを使い､ その中にconfという引用符で畳み掛けるように入力しています｡ つまり､

02:45.560 --> 02:52.820
クラス名のdot find confがマイナス1とは違うことをするのです｡

02:52.820 --> 02:57.680
それは､ マイナス1がノーという意味なので､ 実はコンボリューションがある場合なのです｡ 

02:58.010 --> 03:02.870
まあ､ その場合は重みの初期化を特別に行うことになるのですが｡ 

03:03.200 --> 03:07.220
つまり､ この条件は､ 畳み込み接続がある場合ということです｡ 

03:07.550 --> 03:13.790
ですから､ その場合はどうするかというと､ このように具体的にやりたい重みの初期化を実行するのです｡ 

03:13.790 --> 03:17.790
そうすると､ 直感的でないものはすべてそこに来るわけです｡ 

03:17.810 --> 03:23.390
まず､ weightとescort shapeと呼ぶ変数を作成します｡ 

03:23.940 --> 03:31.020
このコースシェイプのウェイトは､ 基本的にニューラルネットワークのウェイトの形状を含むリストとなるわけです｡

03:31.020 --> 03:35.430
と､ いうわけで､ リスト関数を使って､ リストを作ってみます｡ 

03:36.000 --> 03:43.410
そして､ 内部ではニューラルネットワークのドットウエイトを入力することにしています｡

03:43.410 --> 03:45.990
しかし､ コンボリューション関連では

03:46.290 --> 03:59.100
そして､ これらの重みの形状を得るために､ ドットデータという別の属性を使用し､ そのサイズによって､ 畳み込み接続におけるこれらの重みの形状を得ることができます｡

03:59.490 --> 04:07.560
つまり､ weight shapeは､ ニューラルネットワークの重みと畳み込み接続の形状をリストで含んでいるのだ｡

04:08.330 --> 04:08.660
わかりました｡ 

04:08.660 --> 04:16.430
そこで､ この畳み込み接続の重みを初期化するために､ 2つの値が必要になるのです｡

04:16.430 --> 04:22.790
ファーストは､ 1次元と2次元の積､ 3次元の積です｡ 

04:22.790 --> 04:24.410
それが今､ 手に入れようとしているものなんですね｡ 

04:24.620 --> 04:35.390
そして､ 0次元×2次元×3次元も必要で､ この2つの値を使って重みを初期化する計算をします｡

04:35.390 --> 04:37.850
では､ この最初の製品に取りかかりましょう｡ 

04:37.850 --> 04:44.030
ファンインと呼んでいますが､ これが製品とイコールになるわけです｡ 

04:44.030 --> 04:48.980
そして､ numpyによる関数で､ ショートカットのprod関数を使うことにします｡ 

04:48.980 --> 04:56.560
NP そのprodをnpして､ prodの中に作りたいものを入力するわけです｡ 

04:56.930 --> 05:02.600
そして､ これが私たちのウェイトシェイプの1次元､ 2次元､ 3次元ということになります｡ 

05:02.600 --> 05:06.110
そして､ これを得るために､ 体重の形を取ることができるわけです｡ 

05:06.980 --> 05:10.300
そして､ この3つの次元のインデックスを取得します｡ 

05:10.310 --> 05:18.770
それで､ 1次元から3次元までが含まれ､ 4次元までは含まれないとしたのです｡ 

05:18.770 --> 05:23.990
そしてそれは､ ここの上限が含まれていないために得られるものなのです｡ 

05:24.110 --> 05:26.300
それならば､ それこそ私たちの望むところではないでしょうか｡ 

05:26.300 --> 05:28.880
ファンアウトも同様です｡ 

05:30.660 --> 05:39.330
先ほど言ったように､ ファンアウトは次元の積､ 0倍次元､ 2倍次元､ 3倍次元になります｡

05:39.510 --> 05:45.480
そして､ ここでは､ 含まれる2つから除外される4つまでのインデックスを得ることができるわけです｡ 

05:45.480 --> 05:52.140
つまり､ 2次元と3次元の積が得られ､ それに0次元を掛けることができます｡ 0次元は､

05:52.140 --> 05:58.710
インデックス0のウェイトシェイプ0を使ってアクセスすることができます｡

05:59.010 --> 06:09.180
つまり､ 要約すると､ これはディム1回､ ディム2回､ ディム3回となります｡ 

06:09.950 --> 06:11.660
すぐ下にあります｡ 

06:13.120 --> 06:14.170
ジムゼロ｡ 

06:14.880 --> 06:20.010
タイムズディムからタイムズディム3までの我々の方法､ 形､ 重量のリスト｡ 

06:20.100 --> 06:25.500
それでは､ この2つの値fan inとfan outを使って初期化に進みます｡

06:25.680 --> 06:32.640
新しい値を計算し､ W boundと呼ぶことにします｡ これは､ 関数とpで得られる平方根に等しく､

06:32.640 --> 06:40.620
前とまったく同じようにこのスクリプトによって得られます｡

06:40.620 --> 06:52.230
つまり､ 6の平方根をファンとファンアウトで割ると､ ファンインとファンアウトができるわけです｡ 

06:52.590 --> 06:57.870
つまり､ このWバウンドは､ ある意味､ 暫定的な重みの大きさを表しているのです｡ 

06:57.990 --> 06:59.520
そして､ なぜこれを手に入れたのか｡ 

06:59.520 --> 07:06.240
なぜなら､ これから行うのは､ 重みのテンソルのサイズに反比例するランダムな重みを生成したいからです｡

07:06.240 --> 07:15.090
実際にこれから行うのは､ 新しいネットワーク､ Mを取ることです｡

07:16.030 --> 07:18.040
そして､ その重さを得る｡ 

07:18.370 --> 07:22.240
だから､ まだ属性重量を取ることで､ 次に過剰｡ 

07:22.270 --> 07:25.240
センサーそのものであるデータです｡ 

07:25.910 --> 07:36.290
そして､ この重みのテンソルから､ 重みのテンソルの大きさに反比例するランダムな重みをいくつか生成するのです｡

07:36.960 --> 07:48.570
そこで､ この一様関数に､ マイナスW境界となる下限とプラスW境界となる上限を入力することになります｡

07:49.980 --> 07:52.320
それがウェイトになるわけです｡ 

07:52.320 --> 07:57.380
そして､ 今度はバイアスを初期化する必要があるのですが､ バイアスに朗報です｡ 

07:57.390 --> 07:58.910
もっとシンプルになりそうです｡ 

07:58.920 --> 08:02.130
すべてゼロで初期化します｡ 

08:02.840 --> 08:07.150
そこで､ これらのバイオを取得するために､ モデルからバイオを取得します｡ 

08:07.160 --> 08:09.320
もちろん､ それが私たちのニューラルネットワークです｡ 

08:09.650 --> 08:13.340
そして､ そのための属性がバイアスになる｡ 

08:13.670 --> 08:26.990
これは､ ご想像の通り､ バイアスのテンソルをゼロで埋めるために使用されます｡

08:27.080 --> 08:31.310
さて､ ゼロの場合､ ここでゼロで埋め尽くすことを指定しなければなりません｡ 

08:31.430 --> 08:33.380
というわけで､ ここにインプットしています｡ 

08:33.380 --> 08:33.980
ゼロです｡ 

08:34.370 --> 08:34.760
わかりました｡ 

08:34.760 --> 08:43.400
つまり､ 要約すると､ テンソル重みの大きさに反比例したランダムな重みをいくつか生成し､ バイアスをゼロで初期化するのである｡

08:43.670 --> 08:44.030
わかりました｡ 

08:44.030 --> 08:49.430
つまり､ コンボリューション接続の初期化のためだったんですね｡ 

08:49.550 --> 08:52.700
そして今度は､ 完全な接続のために同じことをする必要があります｡ 

08:53.060 --> 09:00.320
新しい条件を追加します､ Elif､ このトリックを使います､ 最初のクラス名を使います､

09:00.320 --> 09:04.910
この変数は接続の異なる名前を含んでいます｡

09:04.910 --> 09:09.230
そのため､ クラス名が同じであれば､ 定義されたメソッドを使用することになります｡ 

09:10.170 --> 09:18.900
それに対して､ 今回は古典的な線形接続と古典的な人工ニューラルネットワークである完全な接続を引用に入れました｡

09:19.140 --> 09:26.970
それで､ その名前がリニアで､ マイナス1とは違うものにしたいと言うのに､

09:26.970 --> 09:30.060
このトリックを使うんです｡

09:31.010 --> 09:40.940
つまり､ このエンドオブクラス9のファインリニア､ 異なる､ マイナス1は､ 接続がリニアである場合､ つまり､ クラシックなフル接続である場合を意味します｡

09:41.090 --> 09:44.480
では､ その場合､ 重みはどのように初期化するのでしょうか｡ 

09:44.570 --> 09:47.090
まあ､ まったく同じになるんですけどね｡ 

09:47.090 --> 09:55.460
この場合かあの場合のどちらかになるので､ 最初のものを消さない重みのある形状変数を導入する予定です｡

09:55.460 --> 09:57.020
だから､ 同じにはならない｡ 

09:57.020 --> 09:59.210
だから､ それを完全に再利用できるんです｡ 

09:59.690 --> 10:01.250
それから同じ｡ 

10:01.250 --> 10:09.470
今回は､ この3次元の積に等しくないファンを変数に導入します｡

10:09.470 --> 10:13.580
しかし､ 実は今回は単純にイコールになる｡ 

10:15.200 --> 10:16.940
1つ言いましたっけ？

10:17.120 --> 10:23.510
そしてそれは､ 完全な接続の場合､ コンボリューション接続よりも接続数が少ないからです｡ 

10:23.660 --> 10:28.250
NやCNNのコーナーにある直観講義で見たでしょ？

10:28.280 --> 10:32.120
コンボリューションに比べ､ フル・コネクションの方が次元が低い｡ 

10:32.360 --> 10:39.530
つまり､ 基本的にはこの1次元を取り込んで､ それを使ってw boundを計算するために､ fanned

10:39.530 --> 10:42.710
outという変数を用意します｡

10:43.010 --> 10:49.730
そして､ この1次元は､ インデックス・ゼロの重量形状になる｡ 

10:49.730 --> 10:51.290
それがディメンション・ゼロです｡ 

10:51.320 --> 10:55.010
よし､ じゃあwバウンドを計算するのも同じだ｡ 

10:55.310 --> 11:01.430
6の平方根をファンニングとファンアウトの合計で割ったものになるんです｡ 

11:01.580 --> 11:04.460
そうそう､ そうなんです｡ 

11:04.640 --> 11:09.590
それから､ 以前と全く同じというのも良い点です｡ 

11:09.950 --> 11:19.550
重みは一様関数､ バイアスは充填関数を用いて､ 同じような初期化を行った｡

11:19.760 --> 11:24.250
しかし､ 今回はファンインとファンアウトが異なるため､ Wバウンドが異なる｡ 

11:24.260 --> 11:26.060
つまり､ それと同じ原理ですね｡ 

11:26.060 --> 11:27.260
それと同じ発想ですね｡ 

11:27.290 --> 11:38.180
ここで唯一変わったのは､ 完全な接続のための寸法が少なくなったことで､ このランダムな重みを生成するための重みの境界の計算がより簡単になったことです｡

11:39.070 --> 11:42.080
でも､ 今なら間に合うというのがいいところです｡ 

11:42.100 --> 11:50.010
この機能だけでなく､ 2つの道具が揃ったので､ 脳を作り始める準備ができたのです｡

11:50.020 --> 11:51.140
だから､ 待ち遠しいんです｡ 

11:51.160 --> 11:53.310
もちろん､ これが一番楽しみなところでしょう｡ 

11:53.320 --> 11:59.860
これは､ ウォームアップと､ 大事なことの準備のためでしたので､ 次のチュートリアルでそれを処理します｡

11:59.860 --> 12:01.690
まあ､ 実際には何回かチュートリアルが必要なんですけどね｡ 

12:01.690 --> 12:12.010
もちろん､ まず目を作って､ それから入力の時間的特性を学習するためのlshtmを追加して､ アクターとクリティックを担当することを忘れないようにしましょう｡

12:12.010 --> 12:16.810
そして､ その中でこの2つの関数正規化列､ 初期化､ 重みを使うことになります｡ 

12:16.810 --> 12:18.370
だから､ 早くやりたいんです｡ 

12:18.370 --> 12:22.360
これから非常に強力なものを作りますので､ 覚悟しておいてください｡ 

12:22.600 --> 12:23.770
それまではお楽しみに｡ 

12:23.770 --> 12:24.310
I.
