OmniAICreator/Qiita-1.07M huggingface dataset:
Google Cloud Platform (GCP) で独自ドメインを設定する

Google Clout Platform (CGP) でドメイン設定した際の備忘録。

## 概要

CGP 側の作業手順をメインに記載する（お名前.com など、ドメインサービス側のレジストラ設定作業はチョロっとしか記載しない）

## 前提

- GCP で Compute Engine サービスの仮想サーバを構築済みであること（数クリックで出来るから構築説明は割愛。公式ガイドに従えば OK）
- 独自ドメインをどこかしらのドメインサービスで取得済みであること（筆者は「Google Domains」を利用して取得した。通常、最大72時間かかる場合があるが、取得から数分で公開された。さすが Google）
- Web サーバ（Apache, Nginx 等）は仮想サーバに構築済みで、IP アドレスで Web ブラウザから見れるところまで確認済みであること
- あんまり関係ないが、サーバOS： CentOS7

## ドメイン設定手順

### サーバ インスタンスの起動確認

ひとまず、GCP にログイン。
仮想サーバが起動されているか確認。起動してなかったら起動させる（課金内容に注意）
起動すると外部 IP アドレスが払い出される。

### 外部IP アドレス をメモっとく

IP と取得した独自ドメインを紐づけないといけないので、インスタンスの外部 IP アドレスをメモっておく。

- ナビゲーションメニュー > カテゴリ「ネットワーキング」の「VPC ネットワーク」 > 「外部 IP アドレス」を選択

![GCP設定_01.png](https://qiita-image-store.s3.amazonaws.com/0/199602/1fe7a1e4-5ecd-d1c9-80ef-3b2782d08f3c.png)

- 「外部アドレス」の数字をメモる

※ タイプ「エフェメラル」の場合、インスタンス再起動の度に IP アドレスが変わっちゃう。
※ タイプ「静的」にすると IP アドレスは再起動しても固定になるが、予期せぬ課金のキッカケになるので、IP 固定化する理由が薄い場合は「エフェメラル」IP アドレス推奨っす。

## DNS を設定する

- ナビゲーションメニュー > カテゴリ「ネットワーキング」の「ネットワークサービス」 > 「Cloud DNS」を選択

![GCP設定_02.png](https://qiita-image-store.s3.amazonaws.com/0/199602/fcd40c40-b45b-e51d-bb2a-13ecab9651ae.png)

- DNS ゾーンが未作成の場合は、適当な「ゾーン名」を着けて新規ゾーンを作成（作成済みならゾーン名をクリック）
 - 作成時、「DNS名」には取得した独自ドメインを入力すること
 - 新規作成時、NSレコードが（`ns-cloud-a1.googledomains.com.` みたいなのが）４つくらい生成される。これは、レジストラ設定で使う情報。
- ゾーンの設定で「A」レコードの IPv4 アドレスに、先ほどメモった IP アドレスを入力して保存

例えば、既存ゾーンをクリックすると以下のように表示

<img width="900" alt="スクリーンショット 2019-01-04 17.26.58.png" src="https://qiita-image-store.s3.amazonaws.com/0/199602/1554205a-93d6-6094-c8a6-a0dd44d4ca99.png">

ここで「レコードセット追加」を押下で以下。

<img width="476" alt="スクリーンショット 2019-01-04 17.22.22.png" src="https://qiita-image-store.s3.amazonaws.com/0/199602/20674faa-c094-77c3-1915-afc3f548b788.png">

## レジストラ設定（ドメインサービス側）

お名前.com など、ドメインサービス側の各設定画面で、先ほど発行された NS レコードの情報を設定してあげる
（業者によって画面や設定方法が違うので、ここは割愛）
※ もう既に正しい設定が行われているのであれは、この手順はスキップ。

## 確認

ちゃんと設定できてるか、疎通確認。

- 適当に時間をおいて、Web ブラウザから独自ドメインに対してアクセスしてみる
（`http://独自ドメイン名/` など）
- IP アドレスで叩いた時と同様に画面が見れたら成功

## 403 エラー (権限が無い) が出た場合

Web ブラウザからドメイン叩いたらうまくいかないケースがあった。
筆者の環境では、CentOS7 のサーバに Nginx を入れて設定してた。
結果的に、SELinux を一時無効にすることで暫定解決とした。

- SELinux 確認コマンド

```bash
getenforce

# => Encording と出れば、SELinux が有効になっている
```

- 無効化コマンド

```bash
sudo setenforce 0
```

- もう一回確認

```bash
getenforce

# => Permissive と出れば、SELinux が無効
```

これで、ブラウザから問題なく意図したページが表示された。
しかし、根本的な解決では無いので、セキュリティ的に有効でも表示できるような、本来すべき設定があればそちらを行う必要がある。

## HTTPS 対応したい場合

こちらを Qiita 記事をご覧ください。
[「無料 SSL 証明書を発行して簡単に Web サイトを HTTPS 対応させる方法」](https://qiita.com/tomy0610/items/c0310555dace0da60ea2)

以上。
ansibleのcopyコマンドで"Text file busy" のエラー

# 現象
ansibleのcopyコマンドで "Text file busy" のエラー

# 対応
ansible2.2からのオプション[unsafe_writesオプション] (https://docs.ansible.com/ansible/2.5/modules/copy_module.html)を追加

↓こんな感じ

```yaml
- name: Copy to /usr/bin
  copy:
    src: /tmp/hoge
    dest: /usr/bin/
    remote_src: yes
    mode: 0755
    unsafe_writes: true
``` 

# 参考
https://stackoverflow.com/questions/32346342/ansible-text-file-busy-error/45464037#45464037
android開発でContextをどこからでも参照できるように

shared preferenceを使う際に引数で使われるContextをsingletonにして使い回すようにしました

```SingletonContext.kt

import android.app.Application
import android.content.Context

/**
 * contextをどこからでも呼べるようにしたクラス
 */
class SingletonContext : Application() {

    // 他にやることないなら消してもいい
    override fun onCreate() {
        super.onCreate()
    }

    init {
        instance = this
    }

    companion object {
        private var instance: SingletonContext? = null

        fun applicationContext() : Context {
            return instance!!.applicationContext
        }
    }
}
```

それに加えて、AndroidManifest.xmlのapplication以下に追加します。

```AndroidManifest.xml
+            android:name=".SingletonContext"
```

これがわからなくて、ずっとNULL参照でハマってた

- [Android で Context を渡さなくても getString やShared Preference を使えるようにする - ボクココ](https://www.bokukoko.info/entry/2014/05/08/Android_%E3%81%A7_Context_%E3%82%92%E6%B8%A1%E3%81%95%E3%81%AA%E3%81%8F%E3%81%A6%E3%82%82_getString_%E3%82%84Shared_Preference_%E3%82%92%E4%BD%BF%E3%81%88%E3%82%8B%E3%82%88%E3%81%86%E3%81%AB%E3%81%99)
- [adding kotlin class for application context access – JUST DO IT](https://kwagjj.wordpress.com/2017/12/14/adding-kotlin-class-for-application-context-access/)
【今さら】python2.7->python3系への切り替え(windows)

# はじめに
windowsに初期で入っているpython2.7の設定が逐一読み込まれて手間なので、
それをpython3系に変更したい場合のメモ

# 手順1-pythonのインストールパスを確認
コマンド

```
$ which python
/c/Python27/python #Cドライブ直下に存在
$ which python3
which: no python3 in (/mingw64/bin:/usr/bin:/c/Users/user/bin:/c/Python27:/c/Python27/Scripts:/c/ProgramData/Boxstarter:...)
# path情報の全量が表示されたものの、python3に関するpathはないようだ。
```

# 手順2. python3のインストール

[pythonのインストールページ](https://www.python.org/downloads/windows/)に行き、
(32bitPC)Windows x86 web-based installer
(64bitPC)Windows x86-64 web-based installer
をインストール。
これはインストーラファイルなので、ダウンロード後に実行する。
![py-install1.png](https://qiita-image-store.s3.amazonaws.com/0/190712/4318bc56-26d6-96c5-0383-78331959d810.png)

# 手順3. python3のpathを通す。
上画像のチェックボックスを入れて実行する。

# 手順4 python2.7のpathを消して、python3のpathを通す
実行後、以下のpathが通る。

```
- C:\Users\user\AppData\Local\Programs\Python\Python37\Scripts\
- C:\Users\user\AppData\Local\Programs\Python\Python37\
```

その設定をユーザ環境変数、システム環境変数のPath覧に追加する。
![environment_variable01.png](https://qiita-image-store.s3.amazonaws.com/0/190712/5e15e203-5afa-298f-1f0c-469e52890aa3.png)

# 確認

```
$ python
Python 3.7.1 (v3.7.1:260ec2c36a, Oct 20 2018, 14:57:15) [MSC v.1915 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>>
```
C言語でポインタに配列っぽくアクセスできる理由

## 修正

理解不足の点があり誤解を招く表現があったので訂正しました。
Cの理解が足りなかったです。
今後正しい理解を深めようと思います。
言い訳になってしまいますが、配列表現のちょっと変わった使い方があるので共有しようと思ったのがきっかけです。

## はじめに

C言語の入門書では、ポインタの話をしていたら配列的な表現で書かれるとこがあります。

```c:test.c
#include <stdio.h>
#include <stdlib.h>
#define MAX 100

int main(void)
{
    int *test;
    int i;

    test = (int *)calloc(MAX, sizeof(int));
    for (i = 0; i < MAX; i++) {
        test[i] = i; // ここの test[i] は配列（みたい）
    }
}
```


## そもそもCにおける配列とは

~~かなり語弊のある言い方をすると、（他の言語における配列型という意味では）**Cには配列はありません**。~~
これは、私の理解不足でした。

```c
int test[4];
```

上記は `test` という配列を宣言したものですが、 `test` の要素にアクセスする場合ポインタのようにアクセスできます。

## `test[i]` という表記は？

`test[i]` は `*(test + i)` という書き方もできます。
すなわち、 `test` の先頭の要素を指すアドレスに `i` を足したアドレスにアクセスするということです。
勘のいい方は気づいたと思いますが、足し算は交換法則が成り立ちます。
なので、 `*(i + test)` でも問題ありません。
ということは `i[test]` も問題なくアクセスできます。（コンパイルエラーにもなりません）
もちろん `1[test]` なども問題なくコンパイルできます。（あえてすることはありませんが・・・）

## 最後に

C言語において配列とポインタのことについて、ちょっと変わった表現があるので紹介しました。
1次元データを2次元データに変換して深層学習をやる 

#概要
元は1次元スペクトルを入力データとする学習モデルを作成したかった。
入力データが1次元データの場合はLSTMなりDenseが使われるが、今やりたいのは時系列データではないのでLSTMは使う意味はないし、1次元スペクトルも長さが65536なのでこれを全結合してもメモリが不足する。
Conv1Dを使うのが正しい答えだがどういう風にモデル作成をすればいいのか情報が少ない。

そこで1次元スペクトルデータを2次元データに並び替えて既存の2次元データ用(画像用)モデルを学習させてみる。

#並べ方①
```Python:test.py
import numpy as np
X = np.asarray(list(range(65536)))
X = np.reshape(X,(256,256))
print(X)
```
```
[[    0     1     2 ...   253   254   255]
 [  256   257   258 ...   509   510   511]
 [  512   513   514 ...   765   766   767]
 ...
 [64768 64769 64770 ... 65021 65022 65023]
 [65024 65025 65026 ... 65277 65278 65279]
 [65280 65281 65282 ... 65533 65534 65535]]
```
単純に*np.reshape()*を用いて1次元データを2次元データに変換する方法を**並べ方①**とする。
順に並べているだけだが行列の2次元目方向には連続データだが1次元目には連続データではない。
こういうデータに二次元モデルのConv2DやPooling2Dが正しいのかという疑問がある。

#並べ方②
```Python:test.py
import numpy as np
X = np.asarray(list(range(65536)))
X = np.reshape(X,(2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2))
transpose_tuple = (0,2,4,6,8,10,12,14,1,3,5,7,9,11,13,15)
X = X.transpose(transpose_tuple)
X = np.reshape(X,(256,256))
print(X)
```
```
[[    0     1     4 ... 21841 21844 21845]
 [    2     3     6 ... 21843 21846 21847]
 [    8     9    12 ... 21849 21852 21853]
 ...
 [43682 43683 43686 ... 65523 65526 65527]
 [43688 43689 43692 ... 65529 65532 65533]
 [43690 43691 43694 ... 65531 65534 65535]]
```
次にConv2DやPooling2Dを掛けるのに適した並べ方を**並べ方②**とする。
Conv2Dで計算する近接にあるデータは自分の前後のデータで、Pooling2D後にデータサイズの縦横を1/2に縮小した後もその前後のデータが必ず近接に存在するような並べ方を考える。
この並び替えは*np.reshape()*と*transpose()*を使って実装できる。
![range_mat.png](https://qiita-image-store.s3.amazonaws.com/0/299928/68ffd659-102a-32ee-82cf-dfe01695a6ef.png)
#学習
Kerasにおいて1次元データを2次元データに変換してXceptionモデルを用いて学習を行ってみる。
いま入力1次元スペクトルの形は$(32768,2)$なので、これを$(256,128,2)$の二次元画像データのように変換して入力データにする。出力は分子構造を表現するMorganfingerprintで$1024$bitの0,1配列である。
学習のlossは**'binary_crossentropy'**を使う。

```Python:fingerprint_train.py
X = np.asarray(X)
Y = np.asarray(Y)

data_num = X.shape[0]
channel_num = X.shape[-1]
X = np.reshape(X,(data_num,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,channel_num))
transpose_tuple = (0,1,3,5,7,9,11,13,15,2,4,6,8,10,12,14,16)
X = X.transpose(transpose_tuple)
X = np.reshape(X,(data_num, 256, 128, channel_num))
```
```Python:fingerprint_train.py
from keras.applications.xception import Xception

inputs = Input(shape=(256,128,2))
x = Xception(weights=None,input_shape=(256,128,2), include_top=False, pooling='avg')(inputs)
y = Dense(fingerprint_bits, activation='sigmoid')(x)

model = Model(inputs, y)
```
精度はテストデータにおいて予測される出力配列と実際のfingerprintとのtanimoto係数の値で評価を行う。
##結果
各並び方においてepoch150回で3回学習させてみて最後にtanimoto係数を計算させた。
結果は並び方②の方がほんのちょっとだけ良かった。
ただ、実際には1次元スペクトルデータに普通にConv1DとPooling1Dを使ったモデルの方がtanimoto係数は良かったので、1次元データを並び替えて画像用の学習モデルで学習させるメリットはありませんでした。
###並び方①の場合
tanimoto_ave =  0.299359707004864
tanimoto_ave =  0.29289148614259464
tanimoto_ave =  0.30107553163958395
###並び方②の場合
tanimoto_ave =  0.30911110569123995
tanimoto_ave =  0.30068866803832783
tanimoto_ave =  0.3035398883085789
fastlanedでiOSアプリのスクショを自動で撮影

#前書き
タイトルの通り、[fastlane](https://docs.fastlane.tools/)でスクリーンショットを自動で撮ります。
間違ってるとこなんかはそっと指摘してください。

#fastlaneのセットアップ

- bundle init
- Gemfileにfastlaneとcocoapodsを追記
- パス指定して、bundle install --path vendor/bundle
- bundle exec fastlane init



####プロジェクトのディレクトリで

```
bundle init
```

####Gemfileにfastlaneとcocoapodsを記載
<img width="496" alt="スクリーンショット 2018-11-08 12.16.16.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/0fe6e576-396f-1762-7fef-e742213887ea.png">


####bundle install --path vendor/bundleで、パスを指定してインストール
パスを指定しないとシステムにインストールされるみたいです。

####bundle exec fastlane init
もしbundle execをつけなかったらfastlaneがgemの管理下に入らないという事？

これ以降対話形式になって色々質問されるので、答えてください。

---
#xcode側の設定

- sampleUITestUITestsにSnapshotHelper.swiftを追加
- schemeの設定変更
- testExample()にsetupSnapshot(app)app.launch()追加
- スクショ撮りたいとこでsnapshot("single")
- Snapfileを編集

---



####sampleUITestUITestsにSnapshotHelper.swiftを追加
<img width="1441" alt="スクリーンショット_2018-11-08_12_28_27.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/a7ff51fb-06c5-14f4-c5b2-a49f722bbde0.png">

####edit schemeから設定変更
<img width="1572" alt="スクリーンショット_2018-11-07_17_53_54.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/7914b674-3fa9-e20d-5df8-ac6654a6fdcb.png">
<img width="1571" alt="スクリーンショット_2018-11-07_17_54_09.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/e09a04f2-5c50-5da8-a19b-47e2446e83f8.png">

####sampleUITestUITests.swiftのtestExample()にコード追加
<img width="1004" alt="スクリーンショット_2018-11-08_12_39_58.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/9aa6fb33-f7fb-1d1a-a8de-b9ce31f49139.png">


スクショ撮りたいとこでsnapshot("任意の名前")
<img width="1004" alt="スクリーンショット_2018-11-08_12_39_58.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/3fc635ae-8279-82d9-05e1-2a0205f77bb5.png">

####Snapfileを編集
<img width="772" alt="スクリーンショット_2018-11-08_12_44_16.png" src="https://qiita-image-store.s3.amazonaws.com/0/255984/6341aa7e-7c55-e7e8-350f-0d120ba02d6b.png">

#後書き
fastlaneでスクショを撮るにはUITestを使うんですが、今までUITestを使ったことがなかったので苦戦しました。
うまくいかない理由がfastlane側ではなく、UITest側にあると気付くまでが'なん'でした。
UITestのありがたみを少し理解したのでこの調子でUnitTestも使ってみます。
そしてfastlaneでビルドとバージョン番号をインクリメントするのも自動化したい。
C言語における多次元配列の動的な確保

# C言語における多次元配列のメモリ確保
備忘録代わりに今日得た知見をまとめておきます。

## 前提
今回確保するのは、**サイズがあらかじめ決まっている3次元配列**です。
通常であれば次のように書けば事足りるのですが、

```c:static_alloc.c
int a[X][Y][Z];
```
XYZの値があまりにも大きい場合（大きいサイズの3次元配列を確保しようとした場合）に静的領域に収まらないというケースが発生します。
（私は256GBのメモリのマシンに対して1024*1024*4096のfloatの配列を2つ(32GB分)グローバル領域に宣言しようとしてエラーが発生しました。）

なので、今回の記事は動的に要素数が変わる多次元配列の場合は使えないと思います。


## 動的にメモリを確保する方法
そこでC言語で3次元配列を動的確保したいな、と思いネットの海を検索していたら、どうやらポインタのポインタのポインタを宣言して、for文でそれぞれの階層を回すらしいということがわかりました。

この方法に関する記事は 検索エンジンで "C言語 3次元配列 動的確保"とか検索するとたくさん出てきました。

ただし今回のケースでは、配列のサイズは決まっているのでもう少し簡単に各方法はないんだろうか？
と思って、大学の教授に聞いてみたところ、次のような方法で確保できるらしい、ということがわかりました。



```c:dynamic_alloc.c
//3次元配列 a[X][Y][Z]の動的確保の方法
#define X 2
#define Y 2
#define Z 2
//---中略---
int (*a)[Y][Z] = (int(*)[Y][Z])malloc(X*Y*Z*sizeof(int));
```

int型の二次元配列[Y][Z]に対するポインタaに対して、malloc関数によって(X*Y*Z*sizeof(int))byteのメモリを確保します。
malloc関数によって返される型は(void \*)型なので、これを(int(\*)[Y][Z])でキャストすることによって確保できるみたいです。(二次元配列のアドレスでキャストするっていう考えには全然至らなかった…）

##データの配置
この確保方法で、メモリのアドレスはちゃんと順番通りになっているんだろうか？と思って次のプログラムを実行してみました。

```c:Address.c
#include <stdio.h>
#include <stdlib.h>
#define X 2
#define Y 2
#define Z 2
int main(void){
    int (*a)[Y][Z] = (int(*)[Y][Z])malloc(X*Y*Z*sizeof(int));
    //メモリが確保できているか確認
    if(a==NULL){
        printf("Error\n");
    }else{
        printf("OK\n");
    }
    //XYZの値をそれぞれ入れる
    for(int i=0;i<X;i++){
        for(int j=0;j<Y;j++){
            for(int k=0;k<Z;k++){
                a[i][j][k] = i*100 + j*10 + k;
            }
        }
    }
    printf(" XYZ : Address \n");
    //値とアドレスの出力
    for(int i=0;i<X;i++){
        for(int j=0;j<Y;j++){
            for(int k=0;k<Z;k++){
                printf("%4d : %p\n",a[i][j][k],&a[i][j][k]);
            }
        }
    }
    return 0;
}
```
実行結果は次のようになりました。

```text:result.o
OK
 XYZ : Address 
   0 : 0x10c8010
   1 : 0x10c8014
  10 : 0x10c8018
  11 : 0x10c801c
 100 : 0x10c8020
 101 : 0x10c8024
 110 : 0x10c8028
 111 : 0x10c802c
```

intは4byteなのできちんと連続にデータを取ることができているようです。
forで回したりするよりめっちゃ楽だし、これを使っていこう。
[SeleniumWebdriver][Ruby]ブラウザを操作している最中にPopupを表示させる

# SeleniumWebdriverでブラウザを操作している最中にPopupを表示させる
これを試してみようと思ったきっかけは、さらっとログインまでは自動でやって、ログインしたら手動で操作したい。
という場面があったからです。
が、SeleniumWebdriverではログインするコードを書くとどうでしょう。
ログイン後に終了してしまいますね。

で、以下の2点を同時にクリアする方法はないかなと試行錯誤した結果になります。

```
・ブラウザを開いてログインまで自動でやって欲しい
・でもテストが終わっても勝手に閉じないで欲しい
```

## 実際に作ってみよう
```ruby:Acces.rb
require 'win32ole'

# 自由時間開始
puts '========== FreeStyle START !! =========='

def show(msg,title)
  wsh = WIN32OLE.new('WScript.Shell')
  wsh.Popup(msg, 0, title)
end
show("もうい～かい？", "+++")

puts '========== FreeStyle END !!   =========='
# 自由時間終了
```

## 動かしてみると
プロンプト上では以下のようになり、処理が停止します。

```
> Access.rb
========== FreeStyle START !! ==========
```
これはPopupに表示されるボタンの入力を待っている為です。
Popupに表示させるボタン等の引数については[こちら](https://support3.kaonavi.jp/scene-function/chart-board/002/)が詳しく書いてあったので、参考にしていろいろ試してみるといいですね。

## ポップアップは？
以下のポップアップが表示されます。
OKボタンを押すまでは、ブラウザは起動したままとなりますので、手動で操作が可能です。
![popup2.PNG](https://qiita-image-store.s3.amazonaws.com/0/277582/c2de7ef3-c533-1607-783d-edbb1903e6c8.png)

## 他に使い道は？
えーっと、例えば自分のPC上でE2Eツールを使って軽く自動化したい！みたいな時、
アサーションに PASS(変数)や FAIL(変数)をインクリメントさせることで、
数字の計上ができますので、それをPopupに載せるように以下を指定してみると

```
def show(msg, title)
  wsh = WIN32OLE.new('WScript.Shell')
  wsh.Popup(msg, 0, title, 0)
end
show("PASS：#{$PASS}\nFAIL：#{$FAIL}", "TEST RESULT")
```

![test_result_popup2.png](https://qiita-image-store.s3.amazonaws.com/0/277582/527cdfbc-b52e-fba3-8256-8be7b1ef6793.png)

と、このように結果をポップアップに表示してくれて、OKボタンを押さない限りゆっくり確認できます。とか。
・・・あんまりないですかね。

個人的にはこれは軽くブラウザ触りたいって時に重宝してますので、
もし同じ感覚で触る方がいらっしゃれば、是非参考にしていただければorこんなのもあるよ！など教えていただければと思います。
ある文字の「直後」で文字列を切り分ける（JavaScript）

「長い文字列を配列に切り出す」処理はよく必要となりますが、ときには手こずったりもします。

今回は、`'foo_bar_baz_quz'`のような文字列を、アンダーバーの直後で区切って`['foo_', 'bar_', 'baz_', 'quz']`のようにしようとして、きれいな方法はないかと探し回った話です。

## `String.prototype.split`

まず、「文字列を配列に切り分ける」といって真っ先に出てくるであろうものが、`String.prototype.split`（[MDN](https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Global_Objects/String/split)）です。

### いちばん平凡な挙動

`.split`の引数に文字列を書くと、そこで切れた上で切れ目の文字は削除されます。とりあえず、`str.split('_')`のようにすれば切り分けはできますが、削除された`_`を各要素に戻す必要が出てきます。

### 0文字にヒットさせる

`.split`の引数としては正規表現も指定できますが、正規表現に**言明**と呼ばれる機能があります。`^`や`$`は使う人も多いかと思いますが、文字ではなく文字と文字の間にマッチさせることが可能なのです。

ただ、JavaScriptの正規表現には先読みはあっても戻り読みがないので、`str.split(/(?=_)/)`のようにしてアンダーバーの「直前の位置」を切れ目にすることはできますが、直後はうまく行かなさそうです。

### 切れ目も取得する

`.split`に与える正規表現としてキャプチャのカッコが入ったものを与えると、キャプチャされた中身が結果の配列に追加されるようになります。ただ、素直に`str.split(/(_)/)`のようにしても、`foo, _, bar,`のように`_`だけで1つの要素になってしまいます。

ここで気分を変えて、`foo_`全体が切れ目になるように、`/([^_]*_)/`を切れ目にしてみれば、一体として取ることができるようになります…が、「切れ目」どうしが連続するので、`'foo_', '', 'bar_'`のようにから文字列が入ってしまいます。ただ、空文字列はfalsyなので、`.filter(str => str)`のようにして比較的容易に取り除けはします。

## 別なメソッドを使ってみる

「連続して正規表現にヒットさせる」という戦略を取るのであれば、別に`split`である必要性はなくなります。別な正規表現のメソッドを使ってみましょう。

### `RegExp.prototype.exec`

ふつうに正規表現をマッチさせるメソッドです。`/([^_]+_)*/`のようなものをマッチングさせてみたのですが、カッコを`*`などで複数回適用してもキャプチャされるものの数は増えず、最後の1つしかキャプチャできませんでした。これでは切り分けには使えません。

### `String.prototype.match`

`.match`の場合、`/.../g`となっている正規表現を使えば、一度に複数個をマッチさせることができます。結果、`'foo_bar_baz_quz'.match(/([^_]*_|[^_]+$)/g)`のような形で、目的の配列を一発で得られるようになりました。

## 結論

正規表現は、書き方だけでなく、どのような形で使うかでもできることは違ってくる
NOTE: NodeList に NodeList の連結と forEach 処理

**Concat nodelists** and use `forEach` method
referred from [Stack Overflow](https://stackoverflow.com/questions/37552933/concat-two-nodelists/47289655?sfb=2#47289655)

```
unactivate([...tabs, ...codes]);
activate([tab, code]);

function activate(elms) {
    Array.prototype.forEach.call(elms, function(elm) {
        elm.classList.add(CLASS_NAMES.ACTIVE);
    })
}
function unactivate(elms) {
    Array.prototype.forEach.call(elms, function(elm) {
        elm.classList.remove(CLASS_NAMES.ACTIVE);
    });
}
```
【はじめてのPostfix】gmail転送

#はじめに
EC2インスタンスにpostfixをインストールしてgmail転送を行います。
ちなみに私はメールサーバの機能や技術背景、プロトコルなどの理解度ゼロ状態です！

#環境
Postfix2.10
CentOS7.5
Apache2.4
Tomcat8.5
macOS10系

#作業開始
##概要の把握
まずはざっくりしたキーワード（"postfix　とは　gmail　連携　構築　設定"など）で適当にググる。そもそもPostfixって何ですか？状態なので概要を理解するところから。SMTP、IMAP、POPについてもさっとお勉強します。
yumでインストールして設定ファイルの#を外しまくって有効化してあげるらしい、を頭に入れる（適当）。

#とりあえずやってみる
##①main.cfの設定変更
[良さげなサイト](http://www.mikitechnica.com/17-postfixgmail.html)を発見したのでありがたく倣います。
まずはメール転送機能を体験したいため、思考停止状態で手を動かします。わからない用語はあとで調べる。
ホスト名とドメイン名はRoute53で事前に取得済みのドメインを設定している状態です、
仮にドメイン名をokome.comとした場合は以下の手順になります。
それ以外はさっと斜めに読んで大丈夫だろうと推測したのでまるっとコピペです！

```
#vi /etc/postfix/main.cf
myhostname = mail.okome.com
mydomain = okome.com
```

##②メール送信テスト
先にご紹介したサイトに倣いmailコマンドを使ってみるがメールが来ない。
うーむと思っていたら送信元のgmailアドレスに以下の不審なログイン試行をブロックしましたとの重大なセキュリティ通知が。

```
不明な端末
時刻：mm前
場所：EC2インスタンスを作成したリージョン　#私はシンガポールリージョンで作成したら"シンガポール"でした
IPアドレス：EC2インスタンスのパブリックIP
```

googleアカウントの最近使用した端末ページで不明な端末からのログインを許可してあげて、mailコマンドのリトライで無事メール受信完了。
mailコマンド叩く→あれ受信しないな…でコマンド叩く、の分も含めて計3通受信しました。

時間切れのため、本日はここまで。
簡単ですが以上です。

#参考にさせていただいたサイト
[【入門】Postfixとは？メールサーバー構築方法と基本設](https://www.kagoya.jp/howto/webhomepage/postfix/)
[SMTPサーバーとは？IMAPやPOPとの違い＆基本の設定方法](https://www.kagoya.jp/howto/rentalserver/smtpserver/)
[CentOS 7 に Postfix をインストールする手順 (yum)](https://weblabo.oscasierra.net/install-postfix-centos7-yum/)
[CentOS7でmailコマンドでgmailにメール送信できるようにする](https://qiita.com/Esfahan/items/6fa613069b13eb7daa17)
正規表現のテストをする (モノリシックなクラスを作る篇)

こう、適当に正規表現をリテラルに書いちゃったりすると、結構脆弱性の温床になっちゃうじゃないですか。

対策はいろいろ思いつきますが、今回はおてがるに実行なやつから書いていきます。

## 汎用的なパターンをまとめる

 * よいところ
    * 似たようなパターンをリテラルでコピペされなくなる
 * わるいところ
    * 意図しない使われかたをされたり、うっかりパターンに手を入れて処理をぶっこわすことがありうる

## クラスにまとめてみる

```RegExpPattern.php
<?php

/**
 * 汎用的な正規表現をこのクラスに記述する
 */
final class RegExpPattern
{
    const DATETIME = '/\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}/';
    const DATE = '/\d{4}-\d{2}-\d{2}/';
}
```

## PHPUnitでテストしてみる

```php
<?php

final class RegExpPatternTest extends TestCase
{
    /**
     * {@see RegExpPattern} に定義された定数が、最低限不正な表現ではないことを保障
     *
     * @dataProvider validRegExpProvider
     */
    public function testValidRegEx($name, $pattern)
    {
        $actual = preg_match($pattern, '');
        $this->assertNotFalse($actual, '不正な正規表現です');
        // 空文字列とマッチするパターンは有り得るが、通常は想定外の挙動
        $this->assertSame(0, $actual, 'このパターンは空文字列 "" とマッチします');
    }

    public function validRegExpProvider()
    {
        $ref = new \ReflectionClass(RegexPattern::class);

        foreach ($ref->getConstants() as $name => $value) {
            yield [$name, $value];
        }
    }
}
```

あとは、[ReflectionClassConstant](http://php.net/manual/ja/class.reflectionclassconstant.php)を活用すれば、さらにおもしろなDocTestに活用できておもしろいですよ(読者への課題とします)。このようなテスト方法については[DocCommentでPHPのユニットテストの書きやすさを劇的に改善する手法 - pixiv inside [archive]](https://devpixiv.hatenablog.com/entry/2016/10/25/093000)に書きました。
archive.phpでカテゴリ名を表示する（リンクあり・なし）#WordPress

WordPressにて、archive.phpにカテゴリ名（タクソノミー名）を表示させたかったときにハマったのでメモ。
以下ではタクソノミー名を「tax_news」としてます :)

##リンクあり

```php:php
<?php echo get_the_term_list( $post->ID, 'tax_news' ); ?>
```

```php:archive.php

<div class="sample-block">

    <?php if ( have_posts() ) : ?>

    <ul class="sample-list">

      <?php
      while ( have_posts() ) : the_post();
      ?>

      <li>
        <a href="<?php the_permalink(); ?>">
          <span class="date"><?php the_time('Y.m.d'); ?></span>
          <div class="category"><?php echo get_the_term_list( $post->ID, 'tax_news' ); ?></div>
          <h3 class="ttl"><?php the_title(); ?></h3>
        </a>
      </li>

      <?php endwhile; ?>

    </ul><!-- /sample-list -->

    <?php else : ?>
    何も投稿がありません。
    <?php endif; ?>


</div><!--/sample-block-->
```

※aタグ（ブロック要素）になるのでspanなどでは囲えない



##リンクなし

```php:php
<?php $sample_terms = wp_get_object_terms($post->ID, 'tax_news'); ?>
<?php foreach($sample_terms as $term): ?>

～～～

<?php echo $term->name ?>

```


```php:archive.php

<div class="sample-block">

    <?php if ( have_posts() ) : ?>

    <ul class="sample-list">

      <?php
      while ( have_posts() ) : the_post();
      ?>

      <?php $sample_terms = wp_get_object_terms($post->ID, 'tax_news'); ?>
      <?php foreach($sample_terms as $term): ?>

      <li>
        <a href="<?php the_permalink(); ?>">
          <span class="date"><?php the_time('Y.m.d'); ?></span>
          <div class="category"><?php echo $term->name ?></div>
          <h3 class="ttl"><?php the_title(); ?></h3>
        </a>
      </li>

      <?php endforeach; ?>
      <?php endwhile; ?>

    </ul><!-- /m-news-list -->

    <?php else : ?>
    何も投稿がありません。
    <?php endif; ?>

</div><!--/sample-block-->
```

##参考
カスタム投稿タイプのターム名出力_WordPress (©luuuing_web)
[http://luuuing-web.com/web/wordpress/terms_name_wordpress/](http://luuuing-web.com/web/wordpress/terms_name_wordpress/)
クラスメソッド・インスタンスメソッドの呼び出し方


メソッドの呼び出し方を整理した

#ポイント

①クラスメソッドかインスタンスメソッドか
②呼び出し位置
③継承

**クラスメソッド**
・クラスメソッドは定義したクラス自身が使えるメソッド
・クラスメソッドの定義はメソッドの前に.selfをつけ、呼び出しは『クラス名.メソッド名(引数)』

**インスタンスメソッド**
・クラスにメソッドを作成するとそれがインスタンスメソッドとなる。特に追加で記述する必要はない
・使用するにはインスタンスを作成(.new)しなければならない

#呼び出し方

```user.rb

class User < ApplicationRecord
#クラスメソッド
def self.hoge
  "hoge"
end
#インスタンスメソッド
def moge
  "moge"
end

end
```

**コンソール(Userクラス外)からの呼び出し**

```
pry(main)>User.hoge
=> "hoge"

pry(main)> u = User.new
pry(main)> u.moge
=> "moge"


【エラー例】

pry(main)>hoge
NameError: undefined local variable or method `hoge' for main:Object
#console(Userクラス外)からの呼び出しなのでレシーバが必要

pry(main)>moge
NameError: undefined local variable or method `moge' for main:Object
#インスタンスを生成していないため呼び出せない
#レシーバがないと呼び出せない

pry(main)>User.moge
NoMethodError: undefined method `moge' for #<Class:0x007fcbef2724b0>
#mogeはインスタンスメソッドなのでクラスからは呼び出せない
```

**Userクラス内の呼び出し**

```user.rb
hoge
# "hoge"

User.hoge
# “hoge"

self.hoge
# “hoge"

u = User.new
u.moge
# "moge"


def self.call
   hoge
  # “hoge”
  User.hoge
  # “hoge"
  self.hoge
  # “hoge”
  u = User.new
  u.moge
  # “moge”
end


def call
  hoge
  #エラー: インスタンスメソッド内でクラスメソッドはレシーバなしに呼び出せない
  User.hoge
  # “hoge"
  self.hoge
  #エラー: selfはインスタンス自身を指すためクラスメソッドは呼び出せない
  u = User.new
  u.moge
  # “moge”
end

【エラー例】

moge
NameError: undefined local variable or method `moge' for main:Object
#インスタンスを生成していないため呼び出せない
#レシーバがないと呼び出せない

User.moge
NoMethodError: undefined method `moge' for #<Class:0x007fcbef2724b0>
#mogeはインスタンスメソッドなのでクラスからは呼び出せない

self.moge
NoMethodError: undefined method `moge' for #<Class:0x007fcbef2724b0>
#selfは自身のクラスを指すのでインスタンスメソッドのレシーバには出来ない
```

#継承とは(ex:pメソッドはなぜ呼び出せるのか)
```user.rb

class User < ApplicationRecord
  def hoge
    p “hoge"
  end

end
```
pメソッドはUserクラス内で定義されていない。
しかし全てのクラスの親クラスであるObjectクラスで定義されUserクラスに継承されているためpメソッドを使える 
Objectクラス
↑
ApplicationRecordクラス
↑
Useクラス

**Objectクラス参考**
[Rubyリファレンス:Object](https://ref.xaio.jp/ruby/classes/object)
https://ref.xaio.jp/ruby/classes/object


#クラスのselfとインスタンスのself
```user.rb
class User < ApplicationRecord
#クラスメソッド
def self.hoge
  p  self
end
#インスタンスメソッド
def moge
  p self
end

end
```

**コンソール**

```
pry(main)>User.hoge
User(id: integer, screen_name: string, country_id: integer, email: string, encrypted_password: string, reset_password_token: string, reset_password_sent_at: datetime,  profile_image: string, japanese_food_shop: integer)

pry(main)>u = User.new(id: 1)
pry(main)>u.moge
#<User id: 1, screen_name: nil, country_id: nil, email: "", created_at: nil, updated_at: nil, first_name: nil, mid_name: nil, last_name: nil, status: nil, japanese_food_shop: nil>

pry(main)>u = User.new(id: 2)
pry(main)>u.moge
#<User id: 2, screen_name: nil, country_id: nil, email: "", created_at: nil, updated_at: nil, first_name: nil, mid_name: nil, last_name: nil, status: nil,  japanese_food_shop: nil>
```
pythonのprint関数

#pythonのprint関数

##「退屈なことはpythonにやらせよう」
初心者である私が上記本を学習中につまずいたポイントを備忘録として残そうと思います。

###第4章　リスト

####文字絵グリッド（演習プロジェクト）

print関数の挙動の違い

成功したパターン

```grid1.py
grid = [['.','.','.','.','.','.'],
         ['.','0','0','.','.','.'],
         ['0','0','0','0','.','.'],
         ['0','0','0','0','0','.'], 
         ['.','0','0','0','0','0'],
         ['0','0','0','0','0','.'],
         ['0','0','0','0','.','.'],
         ['.','0','0','.','.','.'],
         ['.','.','.','.','.','.']]

for y in range(len(grid[0])):
    for x in range(len(grid)):
        print(grid[x][y], end='')
    print()
```

結果

```
..00.00..
.0000000.
.0000000.
..00000..
...000...
....0....
```

今回学んだことは、pythonにおいてインデントが非常に重要であること、および、しっかりとした理解をしなければエラーが簡単に生じてしまうことである。

失敗したパターン１

```py
for y in range(len(grid[0])):
    for x in range(len(grid)):
        print(grid[x][y], end='')
```

```
..00.00...0000000..0000000...00000.....000.......0....
```

失敗したパターン２

```py
for y in range(len(grid[0])):
    for x in range(len(grid)):
        print(grid[x][y], end='')
        print()
```


```
.
.
0
0
.
0
0
.
.
.
0
0
0
0
0
0
0
.
.
0
0
0
0
0
0
0
.
.
.
0
0
0
0
0
.
.
.
.
.
0
0
0
.
.
.
.
.
.
.
0
.
.
.
.
```
MAについて

![image.png](https://qiita-image-store.s3.amazonaws.com/0/257568/3e6b80ce-13eb-2978-8448-5bb622a95248.png)


CCCM入門を読んだまとめ。
内容が広範囲かつ綺麗に構造化されている訳でもないので小分け。
CCCMがあまり馴染みない表現だが簡単にいうとMA。
MAについて。

## 総論
使いこなすために、どんなコンセプトに基づいて、何の目的で開発され、どんな方向性で進んでいるソフトウェアなのかを理解する

## MAとは
- マーケティングオートメーション
- 大別するとBtoB向けとBtoC向けのものがある
- BtoB向けのものは狭義にMAと呼ばれる
- B向けのMAと比べるとC向けのMAは(目的も重要機能も)異なるためCCCMと定義している


CCCMがあまり馴染まないので、以降B向けのMA、C向けのMAとする
## B向けにもC向けにもあるMAの設定機能
- ターゲットのセグメンテーションとコミュニケーションシナリオの設計、実行機能

## B向け
### 目的
- 見込み客管理  

-> 主にBtoBの見込み客管理
### 手法
**ナーチャリング**
見込み客を管理する手法のこと。下記はそのナーチャリングの1つ

- **リードスコアリング**
  - ネットやリアルの行動履歴やその顧客の属性など、複数のデータを指標に「点数」を付けて評価する方法

追求するものとしては主に見込み客の**育成**になる

## C向け
### 目的
- チャネル横断でのマーケティング施策管理

-> 主にBtoCの各チャネル(メール、プッシュ通知、LINE配信、IoTなど)
### 手法
**One-to-Oneマーケティング**
顧客1人1人を把握し、ニーズにしっかり合うようにカスタマイズした製品やサービスを提供することによって顧客満足度を高め、顧客の**LTV**(生涯価値)を最大化しようというマーケティングコンセプト。

- 簡単にいうと長期的にみた時の収益を最大化しようというもの。
- 「市場のシェア」ではなく「顧客のシェア」を重視したもの。
- 義理チョコたくさんもらうより、本命チョコもらえる人を(少しずつ)増やすことを目指す方

これを実現するためのコストがアドテクノロジーの発達によって低下し、かつ精度も上がっていることで注目されている

追求するものとしては、アドテクの範囲でいうと**CPA**(成果単価)や**CVR**(商品購入率)になる

## 書籍情報
岡本 泰治, 橋野 学, BtoC向けマーケティングオートメーション CCCM入門
https://amzn.to/2B1zVdI

## 雑感
どちらかというとC向けの方が業務関連度が高そう
ただあくまで理解としての切り分けでサービスとしては包含していく傾向があるものなため大枠把握にとどまる。(アドサーバー然り)
AWS初心者がアカウント管理運営(AWSアカウント、IAMユーザ）について勉強してみた

## 自分の技術レベルと興味
自部署で初めてAWSを業務適用する必要が出てきて、あわててAWSのお勉強中です。つまり、**絶賛初心者**。
サービス運用するためのルール作りを主導する役割があるため、社内基準やSLAを意識したアカウント管理業務を作る必要あり。

## AWSアカウント、rootユーザ、IAMユーザ
AWSのドキュメント(BlackBelt）を見てお勉強しました。
[Identity and Access Management (IAM)](https://www.slideshare.net/AmazonWebServicesJapan/aws-black-belt-online-seminar-aws-identity-and-access-management-aws-iam)

まず前提として理解すべきことは、上位にAWSアカウントがあって、その配下にIAMユーザを作る。ということ。

### AWSアカウント(root)ユーザー
AWSアカウント作成時のID、アカウントの全てのAWSサービスとリソースへの完全なアクセス権限を持つ。AWSアカウントはAWSのroot権限を保有し、root権限でないとできない操作がある。日常的なタスクにはAWSアカウント(rootユーザー)を使用しないことを強く推奨。つまり、AWS的には、AWSアカウント≒rootユーザーという理解でよさそう。

### IAMユーザ (Identity and Access Management)
AWS操作をよりセキュアにするための認証・許可の仕組み。AWS利用者の認証と、アクセスポリシーを管理。グループ、ユーザー、ロールの作成が可能。１AWSアカウントで5000ユーザーまで作成可能だそう。

## AWSアカウント作成単位や運営方法
では実際にどのような考え方で使っていくのがよいのでしょうか。

### AWSアカウント
AWSアカウントはリソース管理単位やセキュリティ的概念の境界単位に作るのがよさそうと理解しました。具体的にはシステム＆環境毎（開発/ステージング/本番）になるのでしょうか。
環境毎にわけなくてもよさそうだが、アクセスポリシー設定の仕方が複雑そう、かつ事故って開発と本番間違えるリスクを考えると、やっぱり分離すべきかと。
AWSアカウントは、、、だれが持つべきか？運用部門の組織管理者が保有して厳密管理かな。使う局面は・・・どのぐらいあるのだろうか？（未勉強）基本は使わない/使わせないアカウントと思った方がよさそう。

### IAMユーザ
実際に開発運用で使うのはIAMユーザになるだろう。私の組織では共有アカウントは基本NGであることを前提として個人毎に払い出し。開発者、運用者などグループ分けしてIAMポリシーをそれぞれ作っていく。
開発環境はまあまあポリシー緩め。本番環境はポリシー厳しく行う。ルール（特権アカウント管理基準、SLA/OLA）と照合してアカウント管理基準を作る必要あり。

## コンソールのログインのしかた
AWSマネージメントコンソール上で、AWSアカウントとIAMユーザを見ることができる。
![awsconsole1.PNG](https://qiita-image-store.s3.amazonaws.com/0/308692/678d9de2-3812-3d50-6059-a297427ca81f.png)

IAMユーザでログインする場合。上段にAWSアカウント、中段にIAMユーザを書く。

![awsconsole2.PNG](https://qiita-image-store.s3.amazonaws.com/0/308692/53336e82-42af-23f5-5057-e0e8c513a593.png)


AWSアカウントでログインするときはこの画面。ほぼ使うことないので見憶えなかったわあ（すっとぼけ）


## まとめ
AWSアカウントは、組織のセキュリティ的な責任者に承認を得ないと使えないようにすべき。ただ、責任者が独断で使えないようにする必要もあり、どうすべきだろうと考えながらググっていたら、AWSベストプラクティスが提示されていた。あとで読もう。
[AWS アクセスキーを管理するためのベストプラクティス](https://docs.aws.amazon.com/ja_jp/general/latest/gr/aws-access-keys-best-practices.html)


本番環境のIAMユーザーも基本的には同様。こちらはアクセスキー削除なんてできないので、組織の中でちゃんと運営ルール作らないとダメそう。こちらもAWSベストプラクティスを見つけた。
[IAM のベストプラクティス](https://docs.aws.amazon.com/ja_jp/IAM/latest/UserGuide/best-practices.html)

さらに調べてみたらMFAという二段階認証するための機能があるらしい。これも後で読む。
[AWSアカウントを取得したら速攻でやっておくべき初期設定まとめ](https://qiita.com/tmknom/items/303db2d1d928db720888)

## 最後に
Qiitaに初めて投稿してみたが、こんなんでよいのだろうか。投稿が長くてこれでは持たないのでもう少しシンプルになるように頑張ろう。
Rubyで配列の要素を合計するベストな方法

[Ruby でベンチマークを取る方法](https://qiita.com/scivola/items/c5b2aeaf7d67a9ef310a)を読んでいて、配列の合計値の計算方法っていろいろあるよなーと思ったので。

# 配列の要素を合計する方法
1. 素直に一つずつ`each`でループして足していく
2. `Enumerable#inject`にブロック（ないしはProcオブジェクト）を渡す
3. `Enumerable#inject`にシンボルを渡す
4. `sum`メソッド（Ruby2.4以上）

```ruby
# 1
sum = 0
array.each { |i| sum += i }
# 2
# array.inject { |sum, i| sum + i } と等価
array.inject(&:+)
# 3
array.inject(:+)
# 4
array.sum
```

うーん、さすが[TMTOWTDI](http://d.hatena.ne.jp/keyword/TMTOWTDI)

# 結局どれが一番速いの？
というわけで、上記記事のコードを元に、以下のコードでベンチマークを取りました。
`if array.respond_to?(:sum)`としているのは、古いバージョンでも試したためです。

```ruby
require 'benchmark'

array = 1000.times.map { rand }
num_iteration = 50000

Benchmark.bmbm 10 do |r|
  r.report "inject(&:+)" do
    num_iteration.times do
      sum = array.inject(&:+)
    end
  end

  r.report "inject(:+)" do
    num_iteration.times do
      sum = array.inject(:+)
    end
  end

  r.report "each" do
    num_iteration.times do
      sum = 0
      array.each{|x| sum += x}
    end
  end

  if array.respond_to?(:sum)
    r.report "sum" do
      num_iteration.times do
        sum = array.sum
      end
    end
  end
end
```


## 結果
### Ruby 2.5.0
```
                  user     system      total        real
inject(&:+)   4.212000   0.000000   4.212000 (  4.212325)
inject(:+)    2.208000   0.000000   2.208000 (  2.208990)
each          3.700000   0.000000   3.700000 (  3.703916)
sum           0.356000   0.000000   0.356000 (  0.355434)
```

### Ruby 2.3.0
```
                  user     system      total        real
inject(&:+)   4.920000   0.000000   4.920000 (  4.961357)
inject(:+)    4.500000   0.000000   4.500000 (  4.502774)
each          3.890000   0.000000   3.890000 (  3.892442)
```

### Ruby 1.8.7p357
```
                  user     system      total        real
inject(&:+)  15.060000   0.000000  15.060000 ( 15.074112)
inject(:+)    6.190000   0.000000   6.190000 (  6.197370)
each         10.650000   0.000000  10.650000 ( 10.669348)
```

### `sum`が最強
Ruby2.5では他に6倍以上の差を付けて`sum`の圧勝です。
2.4でも結果は同様でした。

ちなみに`sum`はFloatの誤差が小さくなるように実装されているので、結果も他3つより正確です。

`inject(:+)`は2.4で

1. レシーバーが配列で
2. 引数がシンボル

の場合の最適化処理が入ったようで、2.5では速くなっています。

2.3では`each`が多少速いですが、何度かやると入れ替わることもあり、あまり大差はない印象です。

もはや誰も使ってないでしょうが、1.8は`inject(:+)`の圧勝（と言ってもかなり遅い）。ブロック呼び出しが遅いんでしょうか。
いずれにしてもYARVは偉大。

## ちなみに
`inject`のレシーバーが配列、引数がシンボルなら2.4以降では最適化処理が入ると言いましたが、Rubyのソースコードを眺めていると、配列の要素がIntegerだともう一段最適化が入るようです。

そこで、

```ruby
array = 1000.times.map { rand(1000) }
```

として、もう一度2.5で試しました。

```
                  user     system      total        real
inject(&:+)   3.804000   0.000000   3.804000 (  3.823945)
inject(:+)    0.060000   0.000000   0.060000 (  0.058624)
each          2.804000   0.000000   2.804000 (  2.812767)
sum           0.060000   0.000000   0.060000 (  0.059265)
```

おお、`inject(:+)`が`sum`並に速くなりました！
整数なら丸め誤差もないですし、`inject(:+)`もいいかもしれません。

# 結論
Ruby 2.4以降なら、速くて誤差も小さい`Array#sum`ほぼ一択。ただし要素が全て整数なら`inject(:+)`もあり。

Ruby2.3までなら、どれもさほど変わらないのでお好きなものを（個人的には`inject(:+)`が簡潔で好きです）。
ビットコインのマイクロペイメントチャネルの様々な手法について整理する

#何の話？
ビットコインは単位時間当たりに処理できるトランザクション数が少ないという問題を抱えています。このスケーラビリティ問題を解決するために、ブロックチェーンの外でトランザクションを管理するマイクロペイメントチャネルがいくつか提案されています。今回はこれらの提案手法をざっくりと整理します。

#過去のトランザクションの無効化
マイクロペイメントチャネルでは、過去のトランザクションを無効化し、最新のトランザクションのみを有効にする必要があります。例として、Alice と Bob で資金のやり取りを考えます。複数回取引を行い、以下のように資金移動が発生しました。

初期状態
1. Alice : 1BTC, Bob : 1BTC

Alice -> Bob へ 0.5BTC 送金
2. Alice : 0.5BTC, Bob : 1.5BTC

Bob -> Alice へ 1BTC 送金
3. Alice :  1.5BTC, Bob : 0.5 BTC

ここで取引が終了しました。3番目のトランザクションをブロックチェーンにブロードキャストすることが求められます。しかし、Bob が不正に 2番目のトランザクションをブロードキャストすることで、Bob は Alice から 1BTC 奪うことが出来ます。
これを防ぐため、取引の更新の度に過去のトランザクションを無効化することが必要です。


#様々な無効化手法
以下を満たす手法を実現できれば、最新のトランザクションのみが有効になり、安全にマイクロペイメントチャネルが実装できそうです。

1. 過去のトランザクションをブロードキャストしても、ブロックチェーンに(直ぐに)取り込まれなければよい。
2. 罰則を使用し、過去のトランザクションを不正にブロードキャストする動機を無くせばよい。
3. 信頼できる第三者を設定し、トランザクションを管理を任せればよい。

これら 3 つの考え方に基づいたマイクロペイメントチャネルの論文を紹介します。

###1について
locktime を用いて実装します。トランザクションの更新時に、前のトランザクションより短い locktime を設定します。過去のトランザクションを不正にブロードキャストしても、最新のトランザクションの方が locktime が短いので先にブロックチェーンに取り込まれます。

2者間の資金移動:point_down_tone2:
[A Fast and Scalable Payment Network with Bitcoin Duplex Micropayment Channels](https://www.tik.ee.ethz.ch/file/716b955c130e6c703fac336ea17b1670/duplex-micropayment-channels.pdf)

2者間のチャネルを拡張し、複数人での資金移動:point_down_tone2: channel factory のことです。
[Scalable funding of Bitcoin micropayment channel networks](http://rsos.royalsocietypublishing.org/content/5/8/180089)

###2について
過去のトランザクションを不正にブロードキャストした場合、不正を行ったパーティの資金が相手に奪われるような実装を行います。具体的にはトランザクションの更新時に、前のトランザクションの秘密鍵(or それに類する secret)を相手に公開します。過去のトランザクションの秘密鍵が相手に公開され資金が奪われるので、過去のトランザクションをブロードキャストする動機がありません。Lightning Network の実装はこれです。


[The Bitcoin Lightning Network:Scalable Off-Chain Instant Payments](https://lightning.network/lightning-network-paper.pdf)
:point_up_tone2:前半部分で2者間の資金移動について、後半部分で複数人での資金移動を行う Lightning Network の説明を行っています。

上の論文の改善案:point_down_tone2:　秘密鍵を公開するのではなく、それに類する secret を設定
https://github.com/ElementsProject/lightning/blob/master/doc/deployable-lightning.pdf

###3について
信頼できる実行環境であるTEEを、信頼できる第三者に見立てています。TEE を第三者に見立てているだけなので、実際に第三者は必要とせず Alice と Bob のみでチャネルの構築が可能です。Intel SGX (が提供する enclave) を TEE として使用しています。

2者間の資金移動:point_down_tone2:
[Teechan: Payment Channels Using Trusted Execution Environments](https://www.cs.cornell.edu/people/egs/papers/teechan.pdf)

2者間のチャネルを拡張し、複数人での資金移動:point_down_tone2:
[Teechain: Scalable Blockchain Payments using Trusted Execution Environments](https://arxiv.org/pdf/1707.05454.pdf)

###補足
以下の論文で 1 と 2 の手法を簡潔にまとめています。:point_down_tone2:
[Towards Bitcoin Payment Networks](http://homepages.cs.ncl.ac.uk/patrick.mccorry/paymentnetworks.pdf)

Lightning Network のプロトコルを改良した eltoo も面白いです:point_down_tone2:
[eltoo: A Simple Layer2 Protocol for Bitcoin](https://blockstream.com/eltoo.pdf)
しかし SIGHASH_NOINPUT が必要なので現状 Bitcoin に適用できません
虹色 CSS

カラーコードとかRGB値とか毎回調べるのがめんどくさかったので備忘録として残します(あんまり記事がない?)。。。タイトルどおりの検索をかけた人の助けになれば幸いです。

[虹 - Wikipedia](https://ja.wikipedia.org/wiki/%E8%99%B9)によると虹の7色は、<font color="red">赤</font>、<font color="orange">オレンジ</font>、<font color="yellow">黄色</font>、<font color="green">緑</font>、<font color="aqua">水色</font>、<font color="blue">青</font>、<font color="purple">紫</font>の七色とのこと。

7色すべてにCSSカラーネームがついています。wikipediaのページでもCSSカラーネームで色を指定しているようです。

| 色 | CSSカラーネーム | CSSカラーコード | R | G | B |
|:---|---------------:|---------------:|--:|--:|--:|
| 赤 | red | #FF0000 | 255 | 0 | 0 |
| オレンジ | orange | #FFA500 | 255 | 165 | 0 |
| 黄色 | yellow | #FFFF00 | 255 | 255 | 0 |
| 緑 | green | #008000 | 0 | 128 | 0 |
| 水色 | aqua(cyan) | #00FFFF | 0 | 255 | 255 |
| 青 | blue | #0000FF | 0 | 0 | 255 |
| 紫 | purple | #800080 | 128 | 0 | 128 |

- 色見本
  - `#FF0000`
  - `#FFA500`
  - `#FFFF00`
  - `#008000`
  - `#00FFFF`
  - `#0000FF`
  - `#800080`

調べなおしてみるとなかなか面白いですね...緑ってRGBというぐらいですし`#00FF00`かと思っていたのですが、これは`lime`らしいですね、他にも、色の三原色(`magenta`、`cyan`、`yellow`)の内`magenta`(`#FF00FF`)が仲間外れだったり...意外と虹の色って人間による主観が強いのかもしれません。

ここまで読んでくださりありがとうございました。m(_ _)m
VueJSとLaravelを使用してSPAアプリケーションを構築する(Part.01)

##はじめに

**SPA (Single Page Application)**は**HTML5**と**AJAX**を使用してユーザーの経験を向上させ流というWebアプリケーション。まず、任意なWebページをロードする時、SPAは単一のHTMLページをロードします。
その後、ユーザーの要求に基づいてSPAが同じページに他のHTMLをロードし続けます。そんなことを実施するため、SPAは**AngularJS**とか**Backbone.js**とか**VueJS**などという**JavaScript**ライブラリを利用できます。

今回のシリーズでみなさんと一緒に**CRUD**や**認証**や**ルーティング**や**ページネーション**という機能があるSPAフォーラムを構築します。

**利用技術**

- Backend API:
  - [Framework Laravel (PHP framework)](https://laravel.com/)
- Frontend:
  - [VueJS](https://vuejs.org/)
- Database:
  - [MySQL](https://www.mysql.com/)

##LaravelとVueJSでプロジェクト枠を構築する

今回のプロジェクトの間に`Laravel`と`VueJS`を結合することという目的のため（また、`Laravel` はすでに`VueJS`をサポートしています）、私はLaravelプロジェクトのディレクトリにVueJSアプリを作成します。`Laravel Mix`を使用しないで一部のVueJS定型を使用する場合、それは問題がありません。

また、このプロジェクトの間では、複雑なSPAアプリケーションを構築するためによく利用されているライブラリの使用方法も勉強します。例えば：

- **Vue-router:** アプリケーションのルーティング (ルートの定義とVueコンポーネントへのマッピング)。
- **Axios:** HTTPリクエスト（GET, POST, PUT, DELETE...）の要求と応答というHTTPクライアント。
- **VueX:** VueJSの強力なライブラリ (ステータスの保存と管理に役立ちます)。
- **MomentJS:** 時間の管理。
- **Select2** とか **Datepicker**。

##要件

プロジェクトを開始する前に、知識を知っておく必定があります：

- `Laravel`の基礎知識。
- `VueJS`の基礎知識。

次のようなライブラリ管理ツールの使用方法に関する基本的な知識が必要です。

- `コンポーザー`（Laravel）
- `Npm`とか`Yarn`
- `Laravel Mix`のようなツール

今回の記事は以上です。次の記事に環境の設定を紹介致します。
また、私は外国人だから、日本語があまり良くないので、おかしな日本語の使うところがあったら、皆様教えてくださいね。
よろしくお願い致します。
Twitter APIをいじってみた

# 今回のミッション
昔設定していたWelcomeメッセージを削除すること

# １、TwitterのDeveloperアカウントを取得
詳しいことは[この記事](https://qiita.com/tdkn/items/521686c240b0c5bc6207)に書いてあるので割愛
# ２、Twitter公式のDocumentsを漁る
今回はDMのWelcomeメッセージを削除したかったので[これ](https://developer.twitter.com/en/docs/direct-messages/welcome-messages/overview)を読んだ
# ３、twurlをインスコ
どうやらtwurlが必要らしいのでインスコ

```terminal:ターミナル
gem install twurl
```
DeveloperポータルからConsumerKeyとConsumerSecretを回収して代入

```terminal:ターミナル
twurl authorize --consumer-key {CONSUMER-KEY}       \
                --consumer-secret {CONSUMER-SECRET}
```
# ４、DMのリストを取得

```terminal:ターミナル
twurl -X GET "/1.1/direct_messages/welcome_messages/list.json?count=2"
```
この時にcount=2を取得したいメッセージの数を入れる

```json:output
{
  "welcome_messages": [
    {
      "id": "844385345234",
      "created_timestamp": "1470182274821",
      "message_data": {
        "text": "Welcome!",
        "attachment": {
          "type": "media",
          "media": {
            ...
          }
        }
      }
    },
    {
      "id": "844385345238",
      "created_timestamp": "1470182275399",
      "message_data": {
        "text": "Welcome Again!",
        "attachment": {
          "type": "media",
          "media": {
            ...
          }
        }
      }
    }
  ],
  "next_cursor": "NDUzNDUzNDY3Nzc3"
}
```
こんな感じで降ってくるので消したいメッセージのidを調べる
idをゲットしたら

```terminal:ターミナル
twurl -X DELETE /1.1/direct_messages/welcome_messages/destroy.json?id={さっきのID}
```
これに代入して終了
Excel Office 365 > 行/列の入れ替え > Error: コピー領域と貼り付け領域のサイズが違うため、これをここに貼り付けることができません。 > 成功する手順

```txt:動作環境
Windows 8.1 Pro (64bit)
Excel Office 365
```

### 概要

PowerShellのコマンドでWMIを実行しCPU情報をCSV形式で取得。
(参考: [WMIを使って繋がっているHDDがUSB接続かSATA接続か区別する方法のメモ](https://qiita.com/Fushihara/items/623563ab3192de8b5240) by @Fushihara 様. 情報感謝です)

```powershell
PS C:\Users\XXX> Get-WmiObject -query "SELECT * FROM Win32_Processor" | ConvertTo-Csv > C:\Users\XXX
\Desktop/wmi_181113.csv
```

見にくいためEXCELで「形式を選択して貼り付け」の「行/列の入れ替え」をしようとすると

> コピー領域と貼り付け領域のサイズが違うため、これをここに貼り付けることができません。
> 貼り付け領域内のいずれか１つのセルを選ぶか、または同じサイズの領域を選び、もう一度貼り付けてください。

で失敗。
試すうちに成功する条件は見つかった。

### 失敗

1. コピー元選択時にA1セル左上の◢を選択
2. コピー先シートでA1セル左上の◢を選択して「形式を選択して貼り付け」...

### 成功

1. コピー元選択時は複数セルを手動で選択 (例: A1からBG4まで)
2. コピー先シートでA1セル選択して「形式を選択して貼り付け」...

### 備考

行と列の大きさが違うのだろう（正方行列ではない）。
そのため、行と列を入れ替えた時に「大きさが違う」となるのだろう。

### 関連

- [Excel > 行と列を入れ替えて貼り付け > Ctrl + Alt + V, E, Enter](https://qiita.com/7of9/items/a1e86b98b8dce62e5503)
パフォーマンスモニターでメモリ使用率を保存・確認したい

こんにちはtsuttieです(*'▽')
今回はそろそろサポートの終わるWindowsServer2008R2ですが、検証でメモリの使用率を確認したかったのでその方法を記載したいと思います。

#1. なにをしたのか

今回は何をしたかというとWindowsのサーバー負荷をさくっと一時的に確認したかったので、パフォーマンスモニターを使ってみました。タスクマネージャーで見れるような形式で確認したかったのでその方法を記載します。対象はCPUの使用率とメモリの使用率です。

#2. パフォーマンスモニターの値を保存する

パフォーマンスモニターの値の保存は以下の方法で行いました。

1. パフォーマンスモニターを起動＞右クリック＞新規作成＞データコレクターセット
![pf01.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/85fe0363-88f0-97cc-5714-9d2b23ccc62b.png)

2. 名前を設定＞手動で作成するを選択＞次へ
![pf02.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/8f7e6b46-0520-64c9-5389-5abed17828bc.png)

3. パフォーマンスカウンターを選択＞次へ
![pf03.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/8f037958-8e12-2552-2127-cfdeb216853c.png)

4. 記録する値を設定します
4.1 CPU使用率を計測する場合は`¥Processor(_Total)¥% Processor Time`を設定＞次へ
![pf04.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/94a8c284-2ea8-d4b9-aefd-35149b0f7da3.png)
4.2 メモリ使用率を計測する場合は`¥Memory¥Available Mbytes`を設定＞次へ
![pf05.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/9fd3400b-a3e7-7342-bd69-974a98fa2cb2.png)
4.1、4.2について一緒に取得することも可能ですが、今回はそれぞれの"使用率"を計測したいのでそれぞれ作成します。

5. ルートディレクトリに保存したいパスを設定＞次へ
![pf06.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/cbcf0cd1-a016-3136-4609-9adc9d00be2c.png)

6. 完了を選択
![pf8.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/fff0330e-a4c4-74c7-2a5c-71f3274cb36b.png)

7. 作成された定義上で右クリック＞開始
![pf07.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/9f692d1b-2e5a-2691-73dd-1ed2362fc078.png)

これでそれぞれ設定した値の取得が出来ます。

#3 メモリを使用率(未使用率)に変換する

取得した数値ですが、CPUに関しては何もせずとも使用率が表示されます。(取得したのが全体の使用率なので)
しかし、メモリの使用率は取得することが出来ないので、表示を工夫する必要があります。
取得した値はコンピュータ上で実行するプロセスが使用可能な物理メモリの容量ですので、全体のメモリ容量を分母として割ってあげることで、使用可能であるものと使用されているものの比率を直感的に見ることが出来ます。
全体メモリの容量はタスクマネージャー、左下の物理メモリ領域より合計値を取得します。(例として今回は15799MB) ここの数値がMBなので、取得時はMBのほうがよいかと思います。計算しなくて良いので・・・

次に取得したメモリを表示します。保存したパスをから「～.blg」をクリックすると、保存した値が出力されます。数値がそのままグラフとなっているので多少わかりにくいと思います。私の場合スケールが0.001、最大値が100となっていたのでなんとなくでしかわからないという状況でした。
![pf10.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/cbb24e03-a66a-3bb6-fbc7-bc3b1a6a59ee.png)
そこで割合で把握できるようにスケールと最大値を変更します。
上画像の赤枠部分をダブルクリックして、プロパティを開きます。
スケールを1.0に変更
![pf11.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/31270307-1299-dcb3-d15a-776c1d5f6b59.png)
さらに「グラフ」タブより、最大値を先ほど調べたメモリの最大容量に設定し、適用します。
![pf12.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/c4b11316-b92a-f0f3-b2a5-e9790750a431.png)

すると、
![pf13.PNG](https://qiita-image-store.s3.amazonaws.com/0/198205/b7f72f78-4e91-144c-0e5a-408fc9f4b4e2.png)
割合での表示ができます！

上部が使用率、下部が未使用率になっています。

#4 まとめ

今回はパフォーマンスモニターで負荷を調査しました。
比較的簡単に取得できるので検証程度ならいいと思います。
ずっと溜めるのは容量食うので・・・

何かご指摘等ありましたら、コメントいただければ幸いです。
よろしくお願いします。('◇')ゞ
PHPUnitでは環境変数の読み込み順番に注意しよう

# はじめに
* 引き継いだプロダクトのローカル環境がつらみだった
* Dockerで開発環境を作り直すことにした
* 旧環境では通っていたPHPUnitテストが失敗する事象が発生

上記問題の原因が環境変数読み込み順に関係するものでした
環境変数の読み込み順を気にしたことなかったので(PHP初心者)備忘録

# 対象読者
* docker-composeの`env_file`で環境変数をロードしている
* PHPUnitのバージョンが6.5以下
* 環境変数のロード順がわかっていない


# 原因
PHPUnitではデフォルトとして複数の環境変数の読み込みがあった際、後続の読み込み時に同じkeyの環境変数があっても上書きされないという仕様

* 元々テストが通っていた時の環境変数の読み込み順
  *  リポジトリの直下に`.env`と`phpunit.xml`を配置、PHPUnitの環境変数読み込み順として以下のようになっていた
  * 環境変数の読み込み順 `phpunit.xml`→`.env`

* Dockerで環境を用意した時の環境変数のロード
  * `.env`ファイルをdocker-composeの`env_file`を利用して読み込むようにしていた
  * コンテナ起動時に`.envの環境変数読み込みが走る
  * 環境変数の読み込み順 `.env`→`phpunit.xml`

`.env`の環境変数をテスト時に上書きできなくなり失敗していた


# 解決方法
#### PHPUnitを6.5以上にアップデート

```bash
$ composer remove phpunit/phpunit --dev
$ composer require phpunit/phpunit:6.5.13 --dev
```
#### phpunit.xmlの環境変数のオプション追加
`force="true"`をつけると環境変数を上書くことができるようになる

```xml:phpunit.xml
    <php>
        <env name="APP_ENV" value="testing" force="true"/>
        <env name="CACHE_DRIVER" value="array" force="true"/>
        <env name="SESSION_DRIVER" value="array" force="true"/>
        <env name="QUEUE_DRIVER" value="sync" force="true"/>
        <env name="DB_DATABASE" value="db_test" force="true"/>
    </php>
``` 



# 参考リンク
* https://phpunit.readthedocs.io/ja/latest/configuration.html
DJANGO環境で郵便番号⇒住所自動入力（YubinBango api）

#初めに
この記事は、PYTHON3.6.5、DJANGO2.0の環境で
YubinBango (https://github.com/yubinbango/yubinbango) APIを使用して
郵便番号⇒住所自動入力を実現するためのプラクティスです。
YubinBango apiは、HTML内で特定のCLASS定義を設定するだけで
郵便番号⇒住所自動入力が実現できるAPIです。
今回は、自分が使いやすいように
・都道府県（p-postal-code）
・市区町村番地（p-locality p-street-address p-extended-address）
・建物名（自由入力）
の区分で住所を入力するようにします。

#基礎環境の用意
CREATE VIEWで検証しました。

~~~models.py
from django.db import models
class Address(models.Model):
#modelsは、入力に必要な郵便番号と住所を用意

    zip_code = models.CharField(
　　　　verbose_name='郵便番号',max_length=8,blank=True,
    )
    address1 = models.CharField(
        verbose_name='都道府県',max_length=40,blank=True,
    )
    address2 = models.CharField(
        verbose_name='市区町村番地',max_length=40,blank=True,
    )
    address3 = models.CharField(
        verbose_name='建物名',max_length=40,blank=True,
    )
~~~

~~~forms.py
#CLASS定義をattrsに追加

from django import forms
from .models import Person
class AddressForm(forms.ModelForm):

    class Meta:
        model = Address
        fields = ("zip_code", "address1", "address2", "address3")

        widgets = {
            'zip_code':
            forms.TextInput(
　　　　　　　　　#attrsでp-postal-codeを指定
                attrs={'class': 'p-postal-code','placeholder': '記入例：8900053',}, 　
　　　　　　　),
            'address1': forms.TextInput(
　　　　　　　　#attrsでp-regionを指定
                attrs={'class': 'p-region','placeholder': '記入例：鹿児島県'}, 
　　　　　　　),
            'address2': forms.TextInput(
　　　　　　　　#attrsでp-locality p-street-address p-extended-addressを指定
                attrs={'class': 'p-locality p-street-address p-extended-address',　
                    'placeholder': '記入例：鹿児島市中央町１０'}, 
　　　　　　　),
            'address3': forms.TextInput(
                attrs={'class': '','placeholder': '記入例：キャンセビル'}, 
　　　　　　　),
        }

~~~




~~~base.html
#特別な対応は必要なし

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <title>Address</title>
</head>
<body>
{% block content %}{% endblock %}
</body>
</html>
~~~

~~~views.py
#特別な対応は必要なし

class AddressCreateView(LoginRequiredMixin, CreateView):
    """ 登録画面（顧客情報） """
    model = Address
    form_class = AddressForm
    success_url = reverse_lazy('index')
~~~

URLを指定

~~~urls.py　（特別な対応は必要なし）

from django.urls import path
from django.conf.urls import include
from django.contrib.auth import views
from .views import (
   AddressCreateView,
)

urlpatterns = [
    path('', CustomerInfoFilterView.as_view(), name='index'),
]
~~~



テンプレートはDB名+_form

~~~ address_form.html 
#FORMで定義しないCLASS定義を追加

{% extends "base.html" %}
{% block content %}
　　#CLASSにh-adrを追加
    <form method="post" class="h-adr">　
    {% csrf_token %}
　　#CLASSにp-country-nameを追加
    <span class="p-country-name" style="display:none;">Japan</span>　
    {{ form }}
    <button type="submit">save</button>
    </form>

{% endblock %}
~~~

以上、templateとformにCLASS定義を追加するだけで
郵便番号→住所の自動入力が実現できました。
すごく簡単です。