OmniAICreator/Qiita-1.07M huggingface dataset:
VisualStudioCodeのインストールと日本語化

#開発環境について
プログラムの作成はテキストエディタだけでも可能ですが、開発環境を入れることでより便利になります。
無料で使えるツールについて周りの人に聞いたところ、「VisualStudio」か「VisualStudioCode」がいいよとアドバイスいただいたので比較してみます。
#VisualStudio・VisualStudioCodeについて
どちらも、Microsoft製です。
超ざっくり言うと、VisualStudioCodeの方が機能がシンプルで軽量、VisualStudioは有償版・無償版がありより高機能ということでした。

まずはVisualStudioCodeをインストールして使うことにしました。
#VisualStudioCodeの利用
##必要なファイルのダウンロード
インストーラーの公開ページにアクセスします。
https://azure.microsoft.com/ja-jp/products/visual-studio-code/
![2020-02-11_16h16_06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/e49579b2-bbba-4671-5a0f-595b9e6b57c9.png)
ダウンロードボタンから、自分が利用する環境用のインストーラーをダウンロードします。
今回はWindows版UserInstallerを選択して進めていきます。
![2020-02-11_16h16_53.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/ee433090-1606-3a1a-2aa7-dbee436cf843.png)
##インストール
インストーラーを実行し、使用許諾契約書に同意して次へ進みます。
![2020-02-11_16h18_29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/244bd666-e07b-1a76-b373-c4d00cc4da07.png)
追加タスクはデフォルト設定のままでよいと思います（後で変更できるし）。
![2020-02-11_16h19_46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/cd8cb68c-bf13-ff55-29f6-0dda8c0875f0.png)
![2020-02-11_16h20_36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/5b4319fe-9fa2-255b-fad9-b80b8af8fe48.png)
すぐにインストール完了します。
![2020-02-11_16h21_54.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/7ee3eb91-fdb7-7920-034e-c9f143aca447.png)
##日本語設定
起動すると、最初はメニューなどが英語表記になっています。
![2020-02-11_16h22_59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/61f40751-83d3-494d-2644-cd8e9c8d46d0.png)
日本語メニューにする方法はいくつかあるようですが、以下の方法が簡単だと思います。

上部メニューの[View]から[Command Palette]を開きます。
![2020-02-11_16h27_29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/749f16df-58c4-ae6b-9d0b-d73a690ffa51.png)
表示された入力エリアに「Configure Language」と入力し、「Configure Display Language」をクリックします。
![2020-02-11_16h30_22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/9401bcf6-7673-3338-8ebb-03deeeb450e9.png)
続いて表示される選択肢から「Install additional Languages...」をクリックします。
![2020-02-11_16h33_40.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/b53b87e6-89ed-1051-5364-c2fe7c2af419.png)
利用可能な言語パックが表示されるので「日本語（Japanese Language）」を[Install]します。
その後、再起動を求めるメッセージが表示されたら再起動します。
![2020-02-11_16h35_07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/12d18dfc-88b8-50b8-fa78-d9eb98e19f4a.png)
再起動後、[View]メニュー > [Command Palette] > 「Configure Language」と開くと、[ja]の選択肢が増えているのでクリックします。
![2020-02-11_16h37_30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/99fac4fa-20bf-c64c-a38f-ab5e8cd13711.png)
また再起動を求められるので、[Restart]します。
![2020-02-11_16h38_06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/0e3ab10c-dd1a-e8ff-e7e9-42a32603e092.png)
メニューや表示が日本語化されました。
![2020-02-11_16h38_41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/571995/968334ca-175f-b874-2c78-cc1bdd8caa9b.png)

以上で、VisualStudioCodeのインストールと日本語化ができました。
その他の設定は、実際に開発作業をするなかで必要に応じて行っていこうと思います。
pythonで日にちを基準にソートする

## 状況

pythonの辞書でキーに対して値が日にちで入ってるのでソートしたい。

## 試したこと

そもそも辞書だとキーと値があってややこしいので、まずはリストで考える
試しにやってみました。

```
list = [2020-1-2,2019-3-4,2020-2-4]
print(sorted(list))
```

結果

```
[2012, 2014, 2017]
```

なんじゃこりゃ


※どうやら引き算になってたみたいです。完全に盲点でした、教えていただいた方ありがとうございました！

こちらでやったらうまくいきました。

```
list = ['2020-1-2','2019-3-4','2020-2-4']
print(sorted(list))
```



## 辞書を日付基準でソートするためには？
それでは本題です。

リストは日付基準でソートする方法がたくさん出てきたが、辞書はあまりなかったので、今回やり方を考えてみました。

やり方としては

1.辞書を一旦、キーと値をセットの二次元配列に変換
2.二次元配列の状態でソートをかける
3.辞書に戻す

これなら調べて出てきたソートの方法が使える

2の二次元配列で日付基準でソートをかける方法に関しては以下の記事を参考にさせていただきました。
https://cre8cre8.com/python/sort_string_date.htm

## 実際に書いたコード


```
dict = {'panf1':'2020-2-1','panf2':'2019-3-4','panf4':'2020-1-3'}
list1 = []
sorted_dict={}

print(dict)
for i,j in dict.items():
    list2=[]
    list2.append(i)
    list2.append(j)
    list1.append(list2)
print(list1)

sorted_data = sorted(list1,key=lambda x:x[1],reverse=True)
print(sorted_data)

for k in sorted_data:
    sorted_dict[k[0]]=k[1]

print(sorted_dict)


```
ミルクボーイがRPAを説明したら


（自身の[blog](https://rpa.adgj.pw/items/%E3%83%9F%E3%83%AB%E3%82%AF%E3%83%9C%E3%83%BC%E3%82%A4%E3%81%8Crpa%E3%82%92%E8%AA%AC%E6%98%8E%E3%81%97%E3%81%9F%E3%82%89)にもおいてます）

### 前置き

- あくまで個人の見解です。
- 一部誇張または誤解を生むかもしれない表現がございますが、ネタなのでご容赦いただければ。
- ミルクボーイさんありがとう。

### 本編
U: どうもーミルクボーイでーす。お願いしますー。
U: ありがとうございますー。
U: 今、エンターキーをいただきましたけどもね。ありがとうございます。
U: こんなんなんぼあってもいいですからね。
U: ゆーとりますけどもね。


K: あのー、うちのおかんがね、最近流行ってる新しい技術があるらしいんやけど。
U: そうなんや。
K: その名前を忘れたらしいねん。
U: 流行りなのに忘れるってどないしてんねん。
K: いろいろ聞くけどな、全然分からへんねん。
U: ほんだら俺がね、おかんの忘れた新しい技術一緒に考えてあげるから、どんな特徴いってたか教えてみてよー。


K: おかんがいうには、ロボットが人の仕事を代わりにやってくれるんやって言うてた。
U: おーん。
U: **R　P　A　や　な　い　か　い　。**その特徴はもうRPAやがなー。RPAのRはロボットのRやからね。すぐ分かったよこんなもん。


K: わからへんねん。
U: 何がわからへんのよ。
K: いや俺もRPAやと思てんけどな、おかんが言うには、使てるあいだキータイプの音がめっちゃうるさいらしいねん。
U: ほなRPAとちゃうかー。RPAはロボットといいつつも**ソフトウェアやからね**。物理的にキーボード叩いとらんねん、あれは。ほんとに叩いとったらそれ<u>ただのモーレツサラリーマン</u>やから。ほなRPAとちゃうがなそれ。もうちょっと詳しく教えてくれる？


K: どうやらシンプルでたくさん回数こなす仕事に向いてるらしいねん。
U: RPAやないかい。RPAは**数捌きたい仕事を覚えさせて動かすのが肝**やん。もちろん複雑なモンも作れるには作れるけど、**ROI的には単調作業が向いてんねん**。RPAに決まっとるがなー。


K: わからへんのよ。
U: 何がわからんのー。
K: おかんが言うには、ハンコを押す仕事がいちばん向いてるゆうてんねん。
U: ほなRPAとちゃうやないかい。さっきも言うたけど、RPAは現実世界におるわけやないねんよ。そもそも**承認行為の自動化自体に賛否両論**あんねんからな。インスパイアの会社が[ホンマもんのロボット](https://www.watch.impress.co.jp/docs/news/1223797.html)作ってはったけどみんな「それやない」のツッコミの嵐やったんやで。ほなRPAとちゃうやんか。もうちょい何か言ってなかったか。


K: おかんが言うには、ITエンジニアと違う人でも作ることが出来るらしいねん。
U: RPAやがな。日本じゃ**事務職のひとたちでも勉強すればできる言うて触れ込んでる**んやから。何なら俺もエンジニアやないところから異動してRPA仕事にしとるくらいやからね。その特徴はもうRPAしかないやん。


K: わからへんねん。
U: 何でわからへんのよそれで。
K: おれもRPAやと思たんやけどな、おかんが言うには、めちゃくちゃコード書かないと作られへんらしい。
U: ほなRPAちゃうやないか。RPAは「**コーディングがほとんど要らない**」んが新しいってちやほやされとんねん。そのくせツールによっては**コーディング知らんとなかなか難しい**のもあんのよ。あれは調べたら出てくるのもあんねんけど、みんな<u>調べ方知らんくて悩んでしまう</u>のよなー。ほなRPAちゃうやんけ。他になんかいってなかったかー？


K: おかんが言うには、仕事させると爆速で処理してくれるらしいねん。
U: ほなやっぱりRPAやないかい！**人間の操作とは桁違いに速い**し、クリックとかも画面に映ってないうちからやったり、文字も一瞬で大量に打ったりできるんやから！速すぎて、作ってるあいだ本当にちゃんと動いとるんかチェックすんのが大変なくらいやからね。RPAやんそんなもん！


K: わからへんねん。
U: 何でわからへんのよ！もうRPAしかないやん。
K: いや俺もそう思うねんけどな、おかんが言うにはお願いしたこと以外も勝手にやってくれるときがあるらしい。
U: ほなRPAちゃうやないかい！<u>RPAは作った通りに仕事はしてくれる</u>けど、**作ってない仕事は何もせんねん！**むしろそんな気の利くやつあるんなら欲しいくらいやわ。AIとかもあるけど、あれはまだ教えたことが大前提やからね。無から有は生み出してくれんのよー。もうちょい何か言うてなかったか？


K: おかんが言うには、野良がおるらしいねん。
U: RPAやないかい！RPAは現場の部署で自由に作れるけど、ちゃんとマネジメントされないとどんどん**勝手に変な自動化進められて無法地帯になんねん！**そして気づいたら誰も何やってるかわからへんロボットが生まれるんや！えんどゆーざーなんちゃら言うても、ちゃんと親方は必要なんや！


K: でもな、おかんが言うには、RPAではない言うてんねん。
U: ほなRPAとちゃうやないかい！おかんがRPAではない言うとるならRPAちゃうがな！
K: そうやねん。
U: 先言えよ！おれがハンコおすだけの機械やってたときどう思てたん？
K: 申し訳ないなと思って。
U: ほんまに分かれへんがな。どないなっとんねん。


K: おとんが言うには、AIBOとちゃうかって。
U: いや絶対にちゃうやろ！もうええわ！
K&U: どうも、ありがとうございましたー。
Kotlin向けModelMapper的なライブラリ、KMapperを作った

# 2020/3/6追記
当初はこのライブラリの名前を`MapK`としていましたが、`MapK`はオーガナイゼーションの名前として、ライブラリ名は`KMapper`に変更しました。

# 前書き
`Kotlin`向け`ModelMapper`的なライブラリが欲しかったので作りました。
この記事では、`KMapper`の基本的な使い方についてまとめます。
バージョンは`0.1`時点での内容です。

ライブラリのソースコードは`GitHub`に公開してあります。

- [ProjectMapK/KMapper: Mapper Libraly for Kotlin\.](https://github.com/ProjectMapK/KMapper)

# 導入方法
`JitPack`にて公開しており、`Maven`や`Gradle`といったビルドツールから利用できます。
詳しい導入方法は以下のリンクからご確認ください。

- [ProjectMapK / KMapper](https://jitpack.io/#ProjectMapK/KMapper)

# 開発背景
`Java`では、`POJO`に対してオブジェクトからデータをマップできる`ModelMapper`という便利なライブラリが有ります。

一方、このライブラリは当然ですが`Kotlin`には対応していません。
`Kotlin`は基本的にコンストラクタで初期化を完了する一方、`ModelMapper`は「引数無しコンストラクタでインスタンス生成 -> セッターでデータをそれぞれマッピング」という手順での初期化を想定しているためです。

無理やり`ModelMapper`を使って`Kotlin`のオブジェクトを初期化することも不可能ではありませんが、その場合`immutability`や`Null`安全が犠牲になったりと、`Kotlin`の良さが殺されてしまいます。
また、デフォルト引数に関しても利用することができません。
つまり、そういった機能を十全に使おうと思えばマッパーの利用をあきらめ手動で引数を調整して書くしか有りませんでした。

このため、`src`から`Kotlin`のコンストラクタやファクトリーメソッドを呼び出せるようなマッパーライブラリが欲しいと思いました。

# なにができるか
以下のように、`KMapper`を用いることで、`Dst`クラスのコンストラクタを`src`のプロパティから呼び出すことができます。

```kotlin
// KMapperを使わない場合
val dst = Dst(
  param1 = src.param1,
  param2 = src.param2,
  param3 = src.param3,
  param4 = src.param4,
  param5 = src.param5,
  ...
)

// KMapperを使う場合
val newInstance = KMapper(::Dst).map(src)
```

## KMapperの引数
`KMapper`の引数は、基本的にはコンストラクタやファクトリメソッド、インスタンス関数を含むメソッドリファレンス（≒ `KFunction<*>`）です。

クラスを引数とすることで、プライマリコンストラクタ、もしくは`KConstructor`アノテーションを振ったコンストラクタ/ファクトリーメソッドを呼び出し対象とすることも可能です。

### Javaへの対応に関して
基本的に`Java`のクラス・関数には対応しません。
マッピングには`Kotlin`のメタデータを利用していることと、`Java`では引数の名前が取得できない場合があることが理由です。

## srcに指定できる内容
マップ元には以下が指定できます。

- `Map<String, Any?>`
- `Kotlin`クラスのインスタンス
- `Kotlin`クラスのインスタンス、`Map<String, Any?>`、`Pair<String, Any?>`から構成される可変長引数

`Kotlin`クラスのインスタンスからは、`val`や`var`で定義されたプロパティ（`KProperty`）のみを抽出してマッピングを行います。

### Javaへの対応に関して
前述の通り、`val`や`var`で定義されたプロパティのみが対象であるため、`Java`のゲッターからは抽出を行っておりません。
技術的には不可能ではありませんが、現状では敢えて対応するほどでもないと考えています。

# 終わりに
今回は自作の`Kotlin`向け`ModelMapper`的なライブラリ、`KMapper`に関して書きました。

引数間の変換機能なども有りますが、長くなるので個別の記事としてまとめようと思います。
ドキュメント・テスト等足りない部分は多々ありますが、こちらも今後対応していく予定です。

PR、質問等も募集中です。
是非使ってみて下さいm(_ _)m
[RESTful API]パスパラメータ、クエリパラメータ、リクエストボディの違いと設計

## 事の発端
基本フロントのお仕事をしているのですが、RESTfulAPIの設計をしてね、と言われてRESTfulAPIについて色々調べることがありました。
パスパラメータ、クエリパラメータ、リクエストボディの使い分けについてヘ〜〜〜と思ったので、その結果を備忘として残したいと思います。
（かなり基礎的な情報なので、初心者向けです。）

### この記事で書くこと
- パスパラメータ、クエリパラメータ、リクエストボディってHTTPリクエストで言うどれのこと？
- パスパラメータ、クエリパラメータ、リクエストボディにはどういう情報を持たせればいいの？ 

### この記事で書かないこと(この記事を読む上での前提知識)
#### HTTPリクエストとは何か？
こちらの記事に説明を譲ります。
  [「HTTPリクエスト」と「HTTPレスポンス」  / ITSakuraさん](https://itsakura.com/network-http-get-post)
#### RESTful APIとは何か？
こちらの記事に説明を譲ります。
  [RESTful APIとは何なのか  / @NagaokaKenichi さん](https://qiita.com/NagaokaKenichi/items/0647c30ef596cedf4bf2)　　

##パスパラメータ、クエリパラメータ、リクエストボディってどれのこと？
まずパスパラメータ、クエリパラメータ、リクエストボディとは何かについて書いていきます。

###パスパラメータ（Pathparameter）,クエリパラメータ(queryparameter)

URIで送るものがパスパラメータとクエリパラメータです。

```
https://example.com/pathparameter/{pathparameter}?queryparameter1=hogehoge&queryparameter2=fugafuga
```

例を見て貰えばわかるのですが、
URIでドメインの後、？の前に来るものがパスパラメータです。
そして、?の後に来るのがクエリパラメータです。

###リクエストボディ(requestBody)
URIではなく、JSONで送るものです。

```
{
  hoge_name: fugafuga,
  description: hogefugahoge,
}
```
例えば、こんな感じになります。



##パスパラメータ、クエリパラメータ、リクエストボディにはどういう情報を持たせればいいの？
### パスパラメータ
まず、パスパラメータなのですが、ここには **特定のリソースを識別するために必要な情報** を入れます。

例えば↓のようなuserを束ねるgroupというテーブルがあり、そこから特定のグループ(グループ１)に紐づくユーザーを取得したいとします。

groups_table

|group_id  |group_name  |description  |
|---|---|---|
|1  |hoge  |hogeのグループです。  |
|2  |piyo  |piyoのグループです。 |


users_table

|user_id  |user_name  |gruop_id  |description  |
|---|---|---|---|
|1  |hoge  |1  |hogeのグループに属しています。  |
|2  |fuga  |1  |hogeのグループに属しています。 |
|3  |piyo  |1  |hogeのグループに属しています。 |
|4  |inu  |1  |hogeのグループに属しています。 |
|5  |neko  |2  |piyoのグループに属しています。 |

この場合、**groupId=１** は **特定のリソース識別するために必要な情報** なので設計と実際に叩くAPIは以下のようになります。


```markdown:設計
https://example.com/groups/{group_id}
```


```markdown:実際に叩くAPI
https://example.com/groups/1
```

(エンドポイントのgroupsについては好みです。)

### クエリパラメータ
次に、クエリパラメータなのですが、ここには **特定のリソースを操作して取得する際に必要な情報** を入れます。

先ほどのテーブルから、特定のグループ(グループ１)に紐づくユーザーを3件、user_idの降順で取得したいとします。

この場合、**3件** と **user_idの降順** という条件は **特定のリソースを操作して取得する際に必要な情報** なので設計と実際に叩くAPIは以下のようになります。


```markdown:設計
https://example.com/groups/{group_id}?sort=boolean&limit=number
```


```markdown:実際に叩くAPI
https://example.com/groups/1?sort=false&limit=3
```

（sortは昇順がfalse,降順がtrueという設定です。）
その他では、 **検索、フィルタ** などに関する条件がクエリパラメータとして扱われるようです。

### リクエストボディ
最後に、リクエストボディなのですが、ここには **追加、更新する際の内容** を入れます。

先ほどのテーブルから、特定のグループ(グループ１)を更新したいとします。

この場合、**更新する内容** という条件はまんま **追加、更新する際の内容** なので設計と実際に叩くAPIは以下のようになります。


```markdown:設計(URI)
https://example.com/groups/{group_id}
```

```markdown:設計(JSON)
{
  group_name: "string",
  group_description: "string"
}
```


```markdown:実際に叩くAPI
https://example.com/groups/1
```

```markdown:リクエストするJSON
{
  group_name: "hogehogehoge",
  group_description: "hogehogehogeのグループです"
}
```





#まとめ

- **パスパラメータ**
    - URIでドメインの後、？の前に来るやつ
    - **特定のリソースを識別するために必要な情報**
- **クエリパラメータ**
    - URIで?の後に来るやつ
    - **特定のリソース操作して取得する際に必要な情報**
- **リクエストボディ**
    - URIではなく、JSONで送るやつ
    - **追加、更新する際の内容**

こんな感じで心がけるとわかりやすい設計ができるかもしれません。
オライリージャパンのWebAPI theGoodPartsを読み中なので読破したらまた付け加えるかもしれません。

読んでくださってありがとうございました。
認識違いなどありましたら教えてくださると嬉しいです！
初心者がPythonでWebアプリ開発をはじめてみる

# Python初心者がRest APIを作成する

## やりたいこと

1. フレームワークDjangoを使用してRest APIを作成する
2. ORMライブラリを使用してRDBのデータを操作する
3. AWSにて作成したAPPをホスティングする

## 現状

PythonはCSVの処理を少し書いたことがある。基本文法からして怪しい。パッケージマネージャーがpipなのは知ってる。テストフレームワークにpytestがあるのも知ってる。

## やること

1. 基本文法をざっくり確認したうえで、テストを書きながらPythonのコードに慣れる。
2. Djangoを使って簡単なWebAppを作成する。
3. 目的のRestAPIを作成する。
4. AWS上で動作させる。

## 使うもの

- 『独学プログラマ』
ざーっと文法確認するために一読する。

- 『テスト駆動Python』
テストフレームワークの使い方も合わせてこなす。

- "Test-Driven Development with Python"
Djangoを扱ってみる。

一番目はさっさと終わらす。二番目と三番目は可能であれば同時にすすめる。
Python3でプレイリスト（m8u8ファイル）の読み込み

## m8u8ファイルとは
音楽のプレイリストを保存するファイル形式。中身は以下の形式で保存されたテキストファイルです。
ミュージックプレイヤーでプレイリストをエクスポートすると出力される。
m8u8はutf-8、m8uはSJISの文字コードで保存されてることを表す拡張子。

```
#EXTM3U
#EXTINF:456,約束 【ORT】
F:\music\THE IDOLM@STER\765プロダクション\01_約束 【ORT】.flac
#EXTINF:240,Cherry Colored Love
F:\music\THE IDOLM@STER\ミリオンライブ！\01_Cherry Colored Love.wav
```
曲の長さや曲名 → 曲のフルパス → 次の曲 ...と改行して記載してある。
`#EXTINF:456,約束 【ORT】`
　→ 456は曲の長さ[秒],曲名

## データクラス

```python
class M8U8Info : 
    lengthTime = 0
    name = b""
    filepath = b""
    ext=""
```

## 読み込みクラス
1行目は無視して、偶数行から曲名や長さを設定して、奇数行からフルパスを設定するだけ。
書いた後に思ったが、高階関数でもっとスマートな感じでできると思う。

```python
class M8U8Reader :
    def __init__(self, filepath: str, encode='utf_8_sig') :
        p_new = pathlib.Path(filepath)
        with p_new.open(mode='r', encoding=encode) as f:
            self.readData = f.readlines()

    def read(self) :
        m8u8InfoList = []

        for i in range(len(self.readData)) :
            if i == 0 :
                continue
            if i % 2 == 1 :
                extinf = self.readData[i].split(',')
                m8u8 = M8U8Info()
                m8u8.lengthTime = int(extinf[0][8:])
                m8u8.name = extinf[1].strip()
                m8u8.filepath = os.path.abspath(self.readData[i + 1]).strip()
                m8u8.ext = os.path.splitext(m8u8.filepath)[1]
                m8u8InfoList.append(m8u8)

        return m8u8InfoList
```

## メモ
・私が使ってる外部プレーヤーで出力した場合、BOM付きのUTF-8だったため、以下でエンコードした。
`encode='utf_8_sig'`

・Windowsのvscodeで日本語出力するメモ

```python
sys.stdin = io.TextIOWrapper(sys.stdin.buffer, encoding='utf-8')
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding='utf-8')
sys.stderr = io.TextIOWrapper(sys.stderr.buffer, encoding='utf-8')
```
バラバラな例外をまとめてキャッチする　PHP7.1〜

#前書き
 まとめてキャッチできたら楽だよなって思い調べたら、PHP7.1以降なら使えるみたいなので書き方を載せておきます。

##PHP７．１以前の書き方
```php
try
{
　//例外ごとにキャッチを書かなけばならない
}
catch (Exception1 $t)
{
   echo $t->getMessage();
}
catch (Exception2 $e)
{
   echo $e->getMessage();
}
```
##PHP７．１以降の書き方
```php
try
{
//キャッチ一つで複数の例外をまとめてキャッチできる
} catch (Exception1 | Exception2 $e) {
   echo $e->getMessage();
}
```
 
まとめて書くとコードもスッキリして、かなりいいと思いました。
Raspberry Pi 4 と Momo (Ayame Lite) でWebRTC 配信してみる


## はじめに

Raspberry Pi 4 と Momo (Ayame Lite) でWebRTC配信します。
ウソ穴 のWeb版で使用させて頂きたくて、使い方を調べました。

<blockquote class="twitter-tweet"><p lang="ja" dir="ltr"><a href="https://twitter.com/hashtag/%E3%82%A6%E3%82%BD%E7%A9%B4?src=hash&amp;ref_src=twsrc%5Etfw">#ウソ穴</a> Web版の開発状況<br>A-Frame とストリーミングで仮想的に壁に穴を開けた。ストリーミングに時雨堂さんの momo ayame 使用して動画の遅延ほぼゼロにできた。Firefox対応、Chrome,Safari非対応。 <a href="https://t.co/iPopHBqhPw">pic.twitter.com/iPopHBqhPw</a></p>&mdash; j4amountain (@zsipparu) <a href="https://twitter.com/zsipparu/status/1226394042486837253?ref_src=twsrc%5Etfw">February 9, 2020</a></blockquote> <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

## 参考

こちらのサイトの情報を参考にさせて頂きました（ほぼそのまま使わせて頂きました）

- [Raspberry Pi 4 と Momo と Ayame Lite でお手軽 WebRTC 配信](https://gist.github.com/voluntas/35b8c9d4b2edf11493632e22d483d4a4)

## 概要図

概要は（多分）こんな感じです。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274270/8d89f55f-b29d-f9b3-a674-c63b01a4d2d1.png" width="300">


## カメラについて

Raspberry Pi 4 に接続したカメラはこちら

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274270/4e54274e-3b57-0bde-3d2f-eb30a695b2d8.png" width="400">

[参照元](https://www.amazon.co.jp/dp/B00FGKYHXA/ref=asc_df_B00FGKYHXA2491448/?tag=jpgo-22&creative=9339&creativeASIN=B00FGKYHXA&linkCode=df0&hvadid=217932859331&hvpos=1o3&hvnetw=g&hvrand=11332564013545782284&hvpone=&hvptwo=&hvqmt=&hvdev=c&hvdvcmdl=&hvlocint=&hvlocphy=1009309&hvtargid=pla-440151129080)

## 構築

では、作っていきます。ラズパイにssh接続してコマンドベースで構築していきます。


momo-19.12.1_raspbian-buster_armv7.tar.gz　ダウンロードします

```console
$ wget https://github.com/shiguredo/momo/releases/download/19.12.1/momo-19.12.1_raspbian-buster_armv7.tar.gz
```

ダウンロードしたファイルを解凍します

```console
$ tar -zxvf momo-19.12.1_raspbian-buster_armv7.tar.gz
```

はい、これで準備完了（はやっ！）

## 起動

では、さっそく起動します

```console
$ cd momo-19.12.1_raspbian-buster_armv7/
$ pwd
/home/xxx/momo-19.12.1_raspbian-buster_armv7
$ ls
LICENSE  NOTICE  html  momo
$ ./momo --no-audio ayame wss://ayame-lite.shiguredo.jp/signaling momo-ayame-00000001
```
※ `momo-ayame-00000001` はルームIDです。任意の文字列を指定できます。


はい、起動しました（はやっ！ 2回目）

## 動作確認

Windows10で、以下のサイトをブラウザで開き Momoからの映像を確認します。
[https://openayame.github.io/ayame-web-sdk-samples/recvonly.html?roomId=momo-ayame-00000001](https://openayame.github.io/ayame-web-sdk-samples/recvonly.html?roomId=momo-ayame-00000001)

ルームIDを起動時と同じ文字列（今回は`momo-ayame-00000001`）にして、接続ボタンを押し、映像が表示されたら成功です。（クライアントIDは変更なしでOK）

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/274270/cde815da-eb9e-20a0-d558-edb34fb797c7.png" width="250">

## 注意

ayameは、WebRTCでP2Pの通信を行うためのシグナリングサーバなので、配信映像を複数で受信はできません（Momoの別機能で実現できるみたいです）

## おまけ

recvonly.htmlを自サイトに置きたい場合は、以下から取得します。
https://github.com/OpenAyame/ayame-web-sdk-samples

ここから、以下２つを自作Webサーバーに置けば動きます。

- recvonly.html
- main.js

## さいごに

セットアップが簡単でびっくりしました。映像も遅延がほぼ無くて、体感的にはほとんど遅延をかんじませんでした。すごい
AWS Cron式で「第○○曜日」を設定する方法

AWSでCloudWatch Eventsを使おうとして、
クーロン式で「第2日曜日」、「第3土曜日」みたく月次で曜日を指定して動かしたくなったので、調べてみた。

## 設定方法
少し調べた結果、`SUN#4`等でいけるっぽいです。
公式見たら普通に書いてありました。

使用例：毎月第4日曜日の午前9時

```
00 09 ? * SUN#4 *
```
曜日は1~7、もしくはSUN~SATで設定できますが、SUNとかの方がわかりやすいかも？

## 参考記事
公式を確認（結果的にこれで十分でした）
　[リファレンス: Systems Manager の Cron および Rate 式](https://docs.aws.amazon.com/ja_jp/systems-manager/latest/userguide/reference-cron-and-rate-expressions.html) 
基本的な所はこ記事が参考になりました。
　[AWS_Cron式のワイルドカード](https://qiita.com/da-sugi/items/ef3bb45a8a99a4acacb1)
　[cronで第何何曜日にスクリプトを実行するか指定する](https://orebibou.com/2015/11/cron%E3%81%A7%E7%AC%AC%E4%BD%95%E4%BD%95%E6%9B%9C%E6%97%A5%E3%81%AB%E3%82%B9%E3%82%AF%E3%83%AA%E3%83%97%E3%83%88%E3%82%92%E5%AE%9F%E8%A1%8C%E3%81%99%E3%82%8B%E3%81%8B%E6%8C%87%E5%AE%9A%E3%81%99/)

あと、CloudWatch Events設定するときは時差（UTCとJST）を考慮すべしです。
bundle execって必要なの?

`rails s`って書いても、`bundle exec rails s`って書いても同じ動きをするように見えるんですが、何が違うのでしょうか。気になったので調べてみました。

##結論
- `bundle exec`をつけないと、`Gemfile.lock`に基づかずにgemのバージョンが決定される
- `bundle exec`をつけると、`Gemfile.lock`に書かれているバージョンのgemが動く
- `bin/rspec`のように書くと、`spring`の恩恵を受けて動作が早くなる
- `rails`コマンドだけは`bin`を省略しても`bin/rails`と解釈される

だから

- `rails`コマンドは何も付けずに実行
- `bin`ディレクトリにファイルが存在するコマンドは`bin/◯◯`
- それ以外のコマンドは`bundle exec ◯◯`
    - vscode remote container等でコンテナ内で開発してる場合は`bundle exec`不要

##そもそもBundlerとは
- プロジェクト内で使うGemのパッケージ管理ツール。Gemをプロジェクト単位で管理することができる。
- rbenv(rubyのバージョンをプロジェクト単位で管理するツール)のGem版
- `bundle install`コマンドを叩くと、Gemfileに記載されたGemをインストールする

##bundle installした時のGemの保存先
rbenvを使っている場合

```terminal
$ gem which byebug
/Users/***/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/byebug-11.0.1/lib/byebug.rb
```

##参考
- [railsコマンドを実行するときにbundle execをつけた場合とつけない場合の挙動について](https://teratail.com/questions/62084)
- [bundler、bundle execについて　※自分用メモ](https://qiita.com/dawn_628/items/1821d4eef22b9f45eea8)
- [bundle exec と bin/rails の違い](https://teratail.com/questions/120475)
Nodejs(TypeScript)とcacとinquirer.jsでサクッとCLIを作成する

# はじめに

NodejsでCLIツールを作成するときに良さそうなパッケージを見つけて、実際に使ってみたら良かったので紹介していきます。

## 使ったパッケージ

### cac

シンプルでパワフルなコマンドラインインターフェイスを作るためのフレームワーク

[https://www.npmjs.com/package/cac](https://www.npmjs.com/package/cac)

### inquirer.js

対話型のインターフェースを組み込むのに便利

[https://www.npmjs.com/package/inquirer](https://www.npmjs.com/package/inquirer)

## インストール

```terminal
$ npm i cac inquirer
$ npm i --save-dev @types/inquirer
```

## サンプル

`cac` を使ってCLIの骨組みを書いていきます。
下記の例では `cli hello hoge` みたいなコマンドを入力されたときに処理が実行されるようにしています。

```ts:cli.ts
import index from '../src/index'
import cac from 'cac'

const cli = cac()

cli.command('hello [name]', 'Enter your name').action(() => {
  index()
})

cli.help()
cli.parse()
```

`inquirer` を使って対話型のインタフェースを定義していきます。
下記の例では、入力とリストとチェックボックスの対話型インターフェースを定義しています。

```ts:index.ts
import { prompt, Separator, QuestionCollection } from 'inquirer'

export default async (): Promise<void> => {
  const name = process.argv[3]

  if (!name) {
    console.error('Please pass one argument!!')
    process.exit(1)
  }

  const msg = `
    Hello!! ${name} !!!
  `
  console.log(msg)

  // Input
  const inputQuestions: QuestionCollection = [
    {
      type: 'input',
      message: "What's your name",
      name: 'name'
    }
  ]
  await prompt(inputQuestions).then((answers: any) => {
    console.log(JSON.stringify(answers, null, '  '))
  })

  // List
  const listQuestions: QuestionCollection = [
    {
      type: 'list',
      name: 'color',
      message: 'What do you like color?',
      choices: [
        'black',
        'red',
        {
          name: 'orange',
          disabled: 'disabled'
        },
        'green'
      ]
    }
  ]
  await prompt(listQuestions).then((answers: any) => {
    console.log(JSON.stringify(answers, null, '  '))
  })

  // Checkbox
  const checkboxQuestions: QuestionCollection = [
    {
      type: 'checkbox',
      message: 'select',
      name: 'select',
      choices: [
        new Separator(' = Choise A = '),
        { name: 'hoge' },
        { name: 'fuga' },
        { name: 'foo' }
      ],
      validate: (answer: any): boolean | string => {
        if (answer.length < 1) {
          return 'You must choose'
        }

        return true
      }
    }
  ]
  await prompt(checkboxQuestions).then((answers: any) => {
    console.log(JSON.stringify(answers, null, '  '))
  })
}
```

## 実行する

ビルドするのが面倒なので `ts-node` で実行してきます。

```terminal
$ npx ts-node bin/cli.ts hello test

    Hello!! test !!!
  
? What's your name is_ryo
{
  "name": "is_ryo"
}
? What do you like color? red
{
  "color": "red"
}
? select hoge, fuga, foo
{
  "select": [
    "hoge",
    "fuga",
    "foo"
  ]
}
```

## さいごに

サクッと対話型のCLIを作ることができました。
これでCLIを作るときの雛形はできるので、自作CLIを作っていきましょう！
ではまた！！！
【Rails】bundle exec rails db:seedを行って「localhost でリダイレクトが繰り返し行われました。」が出た時の対処法

#エラー発生
db/seeds.rbの中身の変更を行い、`bundle exec rails db:seed`を行ったところ、「localhost でリダイレクトが繰り返し行われました。」のエラーが発生した。

ログは下記の通り。

```
Started GET "/login" for ::1 at 2020-02-11 15:40:29 +0900
Processing by UserSessionsController#new as HTML
  User Load (0.3ms)  SELECT  `users`.* FROM `users` WHERE `users`.`id` = 13 LIMIT 1
  ↳ vendor/bundle/ruby/2.6.0/gems/activerecord-5.2.3/lib/active_record/log_subscriber.rb:98
Redirected to http://localhost:3000/login
Filter chain halted as :require_login rendered or redirected
Completed 302 Found in 1ms (ActiveRecord: 0.3ms)
```

#原因
下記のようにユーザーは10人にした。

```db/seeds.rb
10.times do
  User.create(
      name: Faker::Name.name,
      email: Faker::Internet.email,
      password: '12345678'
  )
end
```
ユーザーカウントするとご覧のようになる。
`irb(main):005:0> User.count
   (0.4ms)  SELECT COUNT(*) FROM users
=> 10`

それに対してサーバーログ上では`User Load (0.3ms)  SELECT  users.* FROM users WHERE users.id = 13`となっており、13人目のユーザを取得しようとしている。
存在してないユーザーを取得しようとするができないためエラーになっている。自分でデータを入れたため、ユーザーが10人という上限を超えて存在していると思われる。

#解決方法
下記コマンドを実行してユーザーを消去。
`User.all.destroy_all`

その後再び`bundle exec rails db:seed`を行い、サーバーを再起動したところ、画面が正常に表示された。
【 Docker＋Nginx＋Django＋RDS】WEBアプリができるまで①Djangoのようこそページへたどり着くまで

# 前置き
独学で、子供の成長アプリを作った時のことを、記録として残していきます。
開発環境はMac。DBはRDSで Postgresを使います。
間違っているところなどあれば、ご連絡お願いします。

　①[Djangoのようこそページへたどり着くまで](https://qiita.com/quantity82/items/e8c2392bf982efb55f80)　<--ここです
　②[NginxでDjangoのようこそページへたどり着くまで](https://qiita.com/quantity82/items/88a6348135e25c661feb)
　③[カスタムユーザーを作ってadminにたどり着く](https://qiita.com/quantity82/items/b3cd6ded5bbb5f3726f3)
　④[ログインログアウトをしよう](https://qiita.com/quantity82/items/8e4b7ce2ef56e60ad392)
　⑤[ユーザー登録（サインイン）機能を作ろう](https://qiita.com/quantity82/items/bbfc7e72d4a65c71e24c)
　⑥[ユーザーごとのデータ登録できるようにする〜CRU編](https://qiita.com/quantity82/items/4d019a4ee475208a5a26)
　⑦[ユーザーごとのデータ登録できるようにする〜削除編](https://qiita.com/quantity82/items/c48fee71b5f8eb766dae)
　⑧[画像ファイルのアップロード](https://qiita.com/quantity82/items/9bcbd25902f6878ee325)
　⑨[身長体重を記録する＠一括削除機能つき](https://qiita.com/quantity82/items/c8e58742eeaa8c0fc954)
　⑩[成長曲線グラフを描いてみよう](https://qiita.com/quantity82/items/619f5ed2a6cd45f7f592)
　⑪[本番環境へデプロイ＋色々手直し](https://qiita.com/quantity82/items/6e91b7ee7a2d7e0fab32)


# Goal
Djangoのようこそページへたどり着く

# 前提
DockerとDocker-composeは開発環境に入っていること。
MacだとHomebrewを使えば簡単に入る。


# Dockerの設定
たぶん、あまり捻りは無い。

```:Dockerfile
FROM python:3.7

ENV PYTHONUNBUFFERED 1

RUN mkdir /code
WORKDIR /code
ADD requirements.txt /code/
RUN pip install -r requirements.txt
ADD . /code/
```
```:requirement.txt 
Django==2.2.2
psycopg2==2.8.4
```
```yml:docker-compose.yml
version: "3"

services:
  db-postgres:
    image: postgres

  web:
    container_name: web
    build: ./web #webの中のmanage.pyを見に行くよ
    volumes:
      - ./src:/code #srcの中をコンテナ内の/codeに繋げるよ
    ports:
      - "8000:8000" #portフォワード
    depends_on:
      - db-postgres #dbは上で指定したやつ
    command: python manage.py runserver 0.0.0.0:8000 #Django開発用サーバ起動
```

この時点のファイルはこんな感じ。

```
.
├── docker-compose.yml
├── src
└── web
    ├── Dockerfile
    └── requirements.txt
```

# Djangoの設定
まずはプロジェクトを作る。
docker-compose.ymlがあるとこで実行。
最後のピリオドを忘れないこと。

```
docker-compose run web django-admin startproject mysite .
```

すると、以下のようにDjangoの各ファイルが作られる。

```
.
├── docker-compose.yml
├── src
│   ├── manage.py
│   └── mysite
│       ├── __init__.py
│       ├── settings.py
│       ├── urls.py
│       └── wsgi.py
└── web
    ├── Dockerfile
    └── requirements.txt
```

Django上でDBの設定をする。
今回はAWSにPostgresのRDSを作ってあるので、そこに繋げる。
ローカルからAWSのRDSへアクセスする場合は、RDSの設定で
パブリックアクセシビリティを「はい」にしないとダメなので注意。

```python:setting.py
DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql',
        'NAME': 'postgres',
        'USER': '*****',
        'PASSWORD': '*****',
        'HOST': '*****',
        'PORT': 5432,
    }
}
```

# さあ確認
Dockerを起動

```
docker-compose up
```
localhost:8000へアクセスする
<img width="1440" alt="スクリーンショット 2020-02-11 13.02.47.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/547363/f18de754-f183-3a9e-d3e0-b422c726874e.png">
AWSCDKでLambda(Nodejs)をTypeScriptのままデプロイする

# はじめに

AWSCDKでNodejsのLambdaをTypeScriptで書いているときに、デプロイする前にJavaScriptにビルドする必要がなくなったので、その方法を紹介します。

## 使うパッケージ

AWSCDK v1.23.0 から `@aws-cdk/aws-lambda-nodejs` というパッケージがリリースされました。
このパッケージを使えばTSをビルドすることなくデプロイすることができます。

実際に何をやっているかというと、デプロイする前に内部でParcelを使ってビルドをしてくれます。
詳しくは[こちら](https://github.com/aws/aws-cdk/commit/02d0e2aa0075eec5e42b6b6a10ddd7a0e53b97c6)を確認してください。

## サンプル

```ts:stack.ts
import cdk = require("@aws-cdk/core")
import { NodejsFunction } from "@aws-cdk/aws-lambda-nodejs"

export class NodejsFunctionStack extends cdk.Stack {
  constructor(scope: cdk.App, id: string, props?: cdk.StackProps) {
    super(scope, id, props)

    new NodejsFunction(this, "NodejsFunction", {
      entry: "lambdaSources/demo_function/index.ts",
      handler: "handler",
      minify: true
    })
  }
}
```

`NodejsFunction` の `entry` に対してTSファイルを指定しています。
これでデプロイをすると `.build` というディレクトリが生成され、そこにビルド後のソースが置かれています。

## さいごに

これで今までLambdaのソースをTypeScriptで書いているときに、デプロイをする前にビルドする必要があったところが不要になったので、地味に嬉しいアップデートでした。
ではまた！！！
gem install pg が上手くいかない時の対処法

##開発環境

ubuntu(wsl)
Ruby 2.5
Rails 5.2

##エラー内容
`bin/rails db:create`を実行すると

```
Could not find gem 'pg (>= 0.18, < 2.0)' in any of the gem sources listed in your Gemfile.
Run `bundle install` to install missing gems.

```  
言われてた通り`bundle install`を実行すると、

```
An error occurred while installing pg (1.2.2), and Bundler cannot continue.
Make sure that `gem install pg -v '1.2.2' --source 'https://rubygems.org/'` succeeds before bundling.
```

`gem install　pg -v 1.2.2`を確認しろとのことなので、`gem install　pg -v 1.2.2`を実行する。

```
To see why this extension failed to compile, please check the mkmf.log which can be found here:

  /home/username/.rbenv/versions/2.5.1/lib/ruby/gems/2.5.0/extensions/x86_64-linux/2.5.0/pg-1.2.2/mkmf.log
extconf failed, exit code 1

Gem files will remain installed in /home/username/.rbenv/versions/2.5.1/lib/ruby/gems/2.5.0/gems/pg-1.2.2 for inspection.
Results logged to /home/username/.rbenv/versions/2.5.1/lib/ruby/gems/2.5.0/extensions/x86_64-linux/2.5.0/pg-1.2.2/gem_make.out
```

##解決策
下記のコマンドを実行して、その後`gem install pg -v 1.2.2`をする。

```
sudo apt install libpq-dev
```

###参考文献
- [gem install pg が失敗するときの対処法](https://qiita.com/tdrk/items/812e7ea763080e147757)
【機械学習】LDAを勉強してみる

# LDAとは
**LDA(Linear Discriminant Analysis)**とは機械学習において変数の**次元削減**に使われるテクニックです。次元削除の代表的なテクニックにPCAもありますが、PCAとの大きな違いは、PCAは教師なし学習であるのに対し、LDA **教師ありの識別モデル**です。


# LDAのメカニズム
LDAの目的は**クラス間分散を最大**にしながら、**クラス内分散を最小**にする境界線を引くことです。
1)クラス間分散

```math
S_b = \sum^g_{i=1} N_i(\overline{x}_i - \overline{x})(\overline{x}_i - \overline{x})^T
```

2) クラス内分散

```math
S_w = \sum^g_{i=1} (N_i-1)S_i = \sum^g_{i=1} \sum^{N_i}_{i=1}(\overline{x}_{i,j} - \overline{x}_i)(x_{i,j} - \overline{x}_i)^T
```
3) 低次元空間への写像

```math
P_{lda} = arg max \dfrac {\left| P^TS_bP\right| }{\left| P^TS_wP\right|}
 
```
4) 判別式
LDAの判別式は、下のように各クラスに対するガウス分布になります。

```math

P(X|y = k) = \dfrac {1}{(2\pi)^{1/2}|\Sigma_k|^{1/2} exp(-\dfrac{1}{2}(X-\mu_k)^t \sum^{-1}_{k}(X-\mu_k))}
```



# scikit learn で LDA

### LDAのパラメター
|パラメター|概要|値|デフォルト|
|---|---|---|---|　
|solver|学習の最適化計算のタイプ|"svd", "lsqr", "eigen"|"svd"(大きいデータセットに適する)|
|shrinkage|"lsqr", "eigen"で使われる、学習データの不足補正|None, "auto", floa(0~1)|None|
|n_components|削減する次元数|int|-|
|store_covariance|共分散行列を計算するかどうか|bool|-|
|tol|SDVのしきい値|float|-|

### 


```python
from sklearn import datasets
from sklearn.discriminant_analysis import LinearDiscriminantAnalysis
from matplotlib import pyplot as plt

iris = datasets.load_iris()
X = iris.data
y = iris.target

target_names = iris.target_names
lda = LinearDiscriminantAnalysis(n_components=2)
X_r = lda.fit(X, y).transform(X) 
```
可視化

```python

colors = ['blue', 'red', 'green']

for color, i, target_name in zip(colors, [0, 1, 2], target_names):
    plt.scatter(X_r[y == i, 0], X_r[y == i, 1], alpha=.8,
                label=target_name)
plt.xlabel('LDA1')
plt.ylabel('LDA2')
plt.legend(loc='best', shadow=False, scatterpoints=1)
plt.title('LDA of IRIS dataset')

plt.show()
```

![download.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/407366/1bb4ac8d-52b0-9439-76a4-3022502e22f4.png)




# LDA の利点と欠点
### 利点
- 多クラス分類問題では、PCAより性能が良い。

### 欠点
- 小さいサンプルサイズには向いていない。
- クラスの事後確率が正規分布に従う必要がある。
- 全てのデータに対し、分散共分散行列は同じである必要がある。(→QDA)


# LDAの応用
- **QDA(Quadratic Discriminant Analysis)**:
クラスごとに分散共分散を計算。
- **FDA(Flexible Discriminant Analysis)**:入力データが線形分離できない時。
- **RDA(Regularised Discriminant Analysis)**：正規化して分散共分散を計算することで、多変数の影響を抑える。

# 参照
 *Priyankur Sarkar, "hat is LDA: Linear Discriminant Analysis for Machine Learning", 2019
https://www.knowledgehut.com/blog/data-science/linear-discriminant-analysis-for-machine-learning*
hugo new で作った記事の日本語が文字化けする問題について

記事を書く前はTermuxの問題かと思っていましたが、調べていくうちに単純にvimの設定の問題だと判明したような、気がします。

## 原因 文字コード iso-2022-jp
`hugo new posts/hoge.md`
このコマンドで生成した記事の日本語**のみ**が文字化けしてしまう。
`:set fenc?` で確認すると「iso-2022-jp」に…。

## 対策 fileencodings=utf-8 のみ
よく分からないまま次の設定にしていたvimさん。


```bash
vim ~/.vimrc
# 開く
set encoding=utf-8
set fileencodings=iso-2022-jp,euc-jp,sjis,utf-8
set fileformats=unix,dos,mac
```
これを、下記へ

```bash
set encoding=utf-8
set fileencodings=utf-8
set fileformats=unix,dos,mac
```
この通り「utf-8」のみに変更しました。快適！

## 感想
hugoのコマンドなのに、vimの設定を変えると解決する理由が分かりませんが、今後の課題にしたいと思います。
### こちらの記事で解決 [vimで文字化けした時の対応](https://qiita.com/meio/items/08143eacd174ac0f7bd5)
Typescript(Nodejs)で某決済システムの3DES暗号化⇔復号

初投稿！！
某決済システムで、3DESの暗号化・復号をすることになったのでメモですφ(..)

# パッケージのインストール

僕はyarnを使ってるので、yarnで記載してます。
暗号化・復号にはcrypto-jsを使います。
XMLリクエストを投げる際にShiftJISに変換する必要がありますので、iconv-liteもインストールしておきます。

```terminal
$ yarn add crypto-js iconv-lite
$ yarn add @types/crypto-js
```

# 準備

### 暗号化・復号に必要な値のパース
3DESで暗号化・復号を行います。
秘密鍵と初期化ベクトルはencでパースしてあげないとだめなんです。
**これのやり方を理解してなくて苦戦しました。**

```typescript
import { enc } from "crypto-js"

const tripleDesEncryptKey = enc.Utf8.parse("xxxx");
const tripleDesIv = enc.Utf8.parse("xxx");
```

### 文字列のパディング
この決済サイトでは暗号化の際のPadding無しなので、暗号化する文字列は8バイトごとに半角スペースで埋める必要があります。

#### 例えば暗号前の文字が3byte"abc"の場合

```text:例
 12345678
"abc     "
```

#### 例えば暗号前の文字が9byte"abcdefghi"の場合

```text:例
 1234567812345678
"abcdefghi       "
```
#### これをtypescriptのコードにすると...

```typescript:pad-space.ts
export function padSpace(input: string): string {
  // ShiftJISに変換する
  const sjisInput = iconv.encode(input, "Shift_JIS").toString();
  const length = sjisInput.length - 1;
  const paddedLength = 8 - (length % 8) + length;
  return sjisInput.padEnd(paddedLength, " ");
}

```
※もっといい方法ないかな...

# 暗号化

```typescript:encrypt.ts
import { TripleDES, mode, pad } from "crypto-js";
import { padSpace } from "./pad-space.ts";
const encrypt: string = TripleDES.encrypt( padSpace("暗号化したい文字列"), tripleDesEncryptKey, {
    iv: tripleDesIv,
    mode: mode.CBC,
    padding: pad.NoPadding
  }
).toString(); // TripleDES.encryptの返り値はWordArrayです。toString()でBASE64文字列として値を返します。
```

# 復号
基本同じ感じです。

```typescript:encrypt.ts
import { TripleDES, mode, pad } from "crypto-js";
const decrypt: string = TripleDES.decrypt( "BASE64で暗号化された文字列"), tripleDesEncryptKey, {
    iv: tripleDesIv,
    mode: mode.CBC,
    padding: pad.NoPadding
  }
).toString(enc.Utf8).trim(); // 8byteごとにスペースで埋められた文字列が返ってくるので、trimしましょう
```

# はまりどころ
phpとかだと秘密鍵と初期化ベクトルはそのまま文字列で値を渡してあげればいいのですが、
enc.Utf8.parseをつかってパースされた値を渡さないといけません。
※これがわからなくて一日ドハマリしました。

# めんどくさい...
Shift JISに変換してますが、マルチバイトな文字列は返ってこないっぽいんで、不要な気がしてます。
そして次からStripeつかいます、ごめんなさい:sweat:
webpack入門して仲良くなりたい～開発環境編～

# 仲良くなりたい

- [基本編](https://qiita.com/gabochi/items/b0bc1d522b12fe124f90)
- 開発環境編 ←今ココ!!
- [Loaders編](https://qiita.com/gabochi/items/1eab632837c9831172f6)
- Plugins編　近日公開予定

Loadersのことを書こうと思っていたんですが、開発をもっと楽にできそうなのでその設定をここにまとめます

前回のファイル構成をここに載せておきます

```
 webpack-friendly-basic
 ├ ─ ─ node_ modules
 ├ ─ ─ package.json
 ├ ─ ─ package-lock.json
 ├ ─ ─ dist
 │     ├ ─ ─ bundle.js
 │     └ ─ ─ index.html
 ├ ─ ─ src
 │     ├ ─ ─ js
 │     │     └ ─ ─ app.js
 │     └ ─ ─ modules
 │           ├ ─ ─ add.js
 │           ├ ─ ─ subtract.js 
 │           ├ ─ ─ multiply.js 
 │           └ ─ ─ divide.js       
 └ ─ ─ webpack.config.js
```


## webpack-dev-server

```
npm install -D webpack-dev-server@3.10.3
```

このパッケージはwebpackを使った開発で使うと便利なやつです
これを入れることで開発がラクになるので入れます
とりあえず実行してみます

```
npx webpack-dev-server
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/251047/07a1f286-2eed-018b-1785-229ad910bdc3.png)

実行すると画像のように、プロジェクトの実行ページのURLがあるのでアクセスすると

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/251047/eee9f327-b41b-f87a-a4f1-a67a8a1e3d63.png)

こんなページだと思います。
バンドルしたファイルを確認する`index.html`は`/dist`にあるのでそれをクリックするとこんな感じだと思います。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/251047/3fce3995-1567-da64-f475-95521126672a.png)

これでは、なにも楽ではないです。

次はビルドしたときに自動でこのブラウザを開くようにします。

```
npx webpack-dev-server --open
```

`--open`をつけることで自動でブラウザの立ち上げを行います。
手間が少し減りました。

## 自動リビルド

次はバンドル対象のファイルに変更があった場合に自動でリビルドがかかるようにします。
そのために`webpack.config.js`の設定を変えます。

```webpack.config.js

const path = require("path");
const outputPath = `${__dirname}/dist`;

// モジュールどうやって出力するか記述します
module.exports = {
  // 実行環境設定
  mode: "development",
  // エントリー ポイントを決めます
  entry: "./src/js/app.js",
  output: {
    // どこにバンドルファイルを出力するか決まます
    path: outputPath,
    // 出力先のファイル名を決めます
    filename: "bundle.js"
  },
   // 追加設定
  devServer: {
    contentBase: outputPath
  }
};
```

この設定をすることで、ブラウザが開いた時の場所の設定ができます。
`webpack.config.js`の変更を反映させます

```
npx webpack
```

自動ビルドする開発環境でブラウザを開きます

```
npx webpack-dev-server --open
```

ブラウザが開かれて、開発者ツールを確認して
`Live Reloading enabled.`と表示されていれば成功です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/251047/115f8e6b-1599-3334-16ab-8d64581878fd.png)

この状態で、バンドルされたファイルの`app.js`や`modules`のファイルの変更が自動で反映されます。
ここで注意しなければならないのは
**バンドルの対象ではない`index.html`の変更は反映されません**

さらに、`/dist`のディレクトリ構成に注意が必要でした

```
 dist
 ├ ─ ─ js
 │     └ ─ ─ bundle.js 
 └ ─ ─ index.html
 ```

このように、`bundle.js`と`index.html`の階層が同列でない場合はなぜか効きませんでした。

```
 dist
 ├ ─ ─ bundle.js
 └ ─ ─ index.html
 ```
これなら効きます

## package.json

最後に`webpack-dev-server --open`というコマンドを短くします
`package.json`を開いて`scripts`に変更を加えます

```package.json
"scripts": {
    "test": "echo \"Error: no test specified\" && exit 1",
    "start": "webpack",
    "dev": "webpack-dev-server --open"
  }
```

`start`と`dev`を加えました
この設定を行うことで、ターミナルでの実行時のコマンドを変えることができます。

`npx webpack`

```
npm start
```

`npx webpack-dev-server --open`

```
npm run dev
```

## ラクになった

自分的にはこれで結構楽になったんじゃないかなと思います。

次こそローダーについて書きます。

何か、ご指摘があれば教えてくれると嬉しいです。
Macのhomebrewでmysqlクライアントのみインストールする

Macのローカルに作った開発環境のmysqlに接続はしたいけどサーバーはインストールしたくなかったのでメモ

### homebrewの確認
homebrewはインストール済みであることが前提です

```
$ brew -v
Homebrew 2.2.2
Homebrew/homebrew-core (git revision fdb53; last commit 2020-01-03)
Homebrew/homebrew-cask (git revision d9c8; last commit 2020-01-03)
```

### mysql確認
```
$ mysql --version
-bash: mysql: command not found
```
入ってません。

### インストール

```bash
brew install mysql --client-only
...
Error: invalid option: --client-only
```
あれ、エラーになってしまうようですね。どうやらこのコマンドだと私の環境ではインストールできないようです。

以下のコマンドでインストール出来ました。

```bash
brew install mysql-client
```

インストールできました。

```bash
...
######################################################################## 100.0%
==> Pouring mysql-client-8.0.18.high_sierra.bottle.tar.gz
==> Caveats
mysql-client is keg-only, which means it was not symlinked into /usr/local,
because it conflicts with mysql (which contains client libraries).

If you need to have mysql-client first in your PATH run:
  echo 'export PATH="/usr/local/opt/mysql-client/bin:$PATH"' >> ~/.bash_profile

For compilers to find mysql-client you may need to set:
  export LDFLAGS="-L/usr/local/opt/mysql-client/lib"
  export CPPFLAGS="-I/usr/local/opt/mysql-client/include"

```

### パスを通す

ログにもありますが、パスを通さないと、「mysql」コマンドで呼び出せないようです。   

```bash
$ mysql --version
-bash: mysql: command not found
```

以下のように.bash_profileに書き込んで、sourceコマンドで即時反映させればOKです。

```bash
$ echo 'export PATH="/usr/local/opt/mysql-client/bin:$PATH"' >> ~/.bash_profile
$ source ~/.bash_profile
```

### 確認

```bash
$ mysql --version
mysql  Ver 8.0.18 for osx10.13 on x86_64 (Homebrew)
```


おつかれさまでした。
ROCKETBOOKを試してみた

# 概要
* ROCKETBOOKでどんなことができるか試してみた
* [公式サイト] (https://rocketbookjapan.com/)
    * 濡れたタオルやティッシュで消せる
    * スマホ連携もOK
* [公式サイトの商品ページ] (https://rocketbookjapan.com/item/fusion_note)
    * 今回はA4サイズのノート版を購入
    * ページの構成は下記の通り。白紙ページ以外にも色々ある
        * タスクリスト（1P）
        * 週間計画シート（2P）
        * 月間カレンダー（1P）
        * OKRシート（1P）
        * アイデアリスト（1P）
        * ドットページ（18P）
        * ラインページ（18P）
* 基本的なイメージ
![pic3.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/259228/68a11abb-75b0-30b6-6f53-61686c61e8fb.jpeg)
    * 公式サイトより

# 結論
* 普通のSustinablenote + スマホ連携 + SNS連携のような機能
* 手書きのノートとタブレットの間くらいの機能や使い勝手や連携状況
* 個人的にはもう一回り小さい方を買えばよかった

# 連携手順
## 0. amazonなどでROCKETNOTEを買う
* 今回はfusionというバージョンのノートサイズを購入

## 1. 普通にノートを書く
* 今回は同梱されていた黒のFRIXIONと後で買った少し細い3色ペンの赤で文字を書いてみました

![pic1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/259228/cbef9def-e514-9a2f-a9f0-ec641972156c.jpeg)

## 2. 連携の設定をする
* ノートの下部にマークが有り、これにマークを付けてどことリンクするのかを決める
* ROCKETのスマホアプリをインストールして、Destinationsでマークに対応する通知先とフォーマットなどを設定する
    * ちなみにSNSごとに1つということはなく、別のマークにSlackの別のチャンネルなどを指定することもできます。]

![pic2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/259228/08a75441-4764-e5cc-f352-ecbc8e6c9cc1.png)

## 3. スマホアプリで写真を取る
* スマホアプリでノートを写す
* ビーコンモードなるものもあるそうですが、今回は検証をしていません。
![Screenshot_20200211-131318.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/259228/bca45922-59ef-3613-dd7f-4ea29c91fed7.png)

## 4. 通知を確認する
* 通知されたSNSで内容を確認する

![pic4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/259228/7508ac6f-c1b5-9d88-9540-f67770801e76.png)

![pic5.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/259228/8c7ee796-aab9-f406-0c5e-e0472eb8f96e.png)

* フォーマットはjpgとpdfが選べるのですが、今回はpdfを選択
    * 普通のスキャナーみたいな解像度で、細いと少しかすれますね
AutomatorでYoutube動画自動再生してみた

# Automatorとは

↓のアイコンでおなじみのMacアプリの操作自動化に使えるアプリです

![automator_logo.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/578529/d36645c5-a385-a102-a37e-230bd008e100.jpeg)

今回はSafariでYoutubeのチャンネルページを開いて動画をクリックして再生させる処理を自動化したいと思います
また、AppleScriptも少し使ってみます

詳細は以下の動画で紹介しています

https://youtu.be/n3sgpBPugos
chainerで、functionSetは無いよって言われた場合の対処

##環境
python2.7 (最終的な)

##起こったこと。
調べながらchainerのサンプルプロジェクト動かそうとしたら、文法エラーが出まくった。
あ、これpython2系じゃないと動かないパターンだなって思って、
phthon2の仮想環境に切り替えて実行したら、
今度は、functionSetなんてインポートできないでござるって言われてしまいました。
そして、ググる。

## 解決方法
ググったら、以下の記事が出てきました。
https://teratail.com/questions/113819

「ダウングレードするか、新しいバージョンのチュートリアルを見つけて」って書いてあったので、
ダウングレードする方法の方が早く動かせると思ったので、インストールしていたchainerを
アンインストールし、ダウングレードすることに。

普通に、pip install chainerやったら、v7.1.0になったので、これはたいへん。
どこまで戻せばいいんだって、バージョンを少しずつ下げてアンインストール、インストールって繰り返して行ったら、
ついに、動いたバージョンを発見。

バージョンは、「v1.17.0」です、動きました。
いや、古スギィ！

でも最新のままだと他のライブラリとバージョン合わなくなったりプログラム修正したりやることが山ほど生まれてしまうし今回個人で勝手にやってるだけなので許してクレメンス。

なので、functionSetを使ってるプロジェクトの場合、
このバージョンを検討してみるとよさそう


## 感想
作業効率を高めるで有名なシェルのfishを使っていたのですが、
こいつのせいで、環境構築に大変苦しみました。(1日中環境構築うまくいかなくて泣きそうになった日もあった)
パスが通っていなかったり。
なので、bashに戻したら、あっという間に環境構築がうまくいきました。

fishさん。見た目かっこよくて好きだったけど、選ばれたのは、bashでした(至言)
[GAE][Rails]Note: Google::Cloud is disabled と表示される

# 事象
develop環境でrailsコマンドを打つと下記が発生

```
Your application has authenticated using end user credentials from Google Cloud SDK. We recommend that most server applications use service accounts instead. If your application continues to use end user credentials from Cloud SDK, you might receive a "quota exceeded" or "API not enabled" error. For more information about service accounts, see https://cloud.google.com/docs/authentication/. To suppress this message, set the GOOGLE_AUTH_SUPPRESS_CREDENTIALS_WARNINGS environment variable.
Note: Google::Cloud::Logging is disabled because the project ID could not be determined. Falling back to the default Rails logger.
Note: Google::Cloud::Debugger is disabled because the project ID could not be determined.
Note: Google::Cloud::ErrorReporting is disabled because the project ID could not be determined.
Note: Google::Cloud::Trace is disabled because the project ID could not be determined.
```

# 対象方法
とりあえずdevelop環境ではLogging等いらないと判断し下記の設定を追加しました。

```ruby:config/enviroments/development.rb

  # gcp設定
  config.google_cloud.use_logging = false
  config.google_cloud.use_debugger = false
  config.google_cloud.use_error_reporting = false
  config.google_cloud.use_trace = false

```


# 参考
[GAE/Rails で Stackdriver Logging を綺麗にするためにログの仕組みを学んだ](https://note.com/_yoshioka/n/n513cbf9fd5ad)
[Rails — Disable Stackdriver in development](https://medium.com/@martin.samami/rails-disable-stackdriver-in-development-79fd746e9bd7)
今月はJava強化月間と決めました

　こんにちは、ヨースケです。[以前](https://qiita.com/ysk75/items/278c52bf4052991eb99d)投稿した記事でコメントしてくださった方ありがとうございます。大変勉強になりました！
## アプリ開発する上での危機感
　その記事でコメントにあったソースコードを見て「このままじゃダメだな」と感じ、もう一度勉強しなおそう！と思いました。こんな書き方があったんだ！という衝撃と自分の勉強不足さがあらわになって今月2月はJavaを隅から隅まで勉強し直そうと決めました。
　次に作る予定があるアプリもありますが、いったんはお休みしてJavaを強化したいと思います。
　まぁ、うつ病のせいで毎日がっつりはできないんですが少しずつでも進めていきます！
塩基配列のAT含量（CGまで）をちゃちゃっと計算させるシェルコマンド

#AT含量計算に無駄な機能はいらない
AT含量計算なんて、そこら中にツールがあるので探した方が早い。

が、自分の場合、コピペした塩基配列とかFASTAからとかbedtools getfasta出力からAT含量をちゃちゃっと計算したい瞬間が多く、

１．ターミナルで動く
２．カスタムできる
３．後の描画用にATCGそれぞれで出力してほしい

を条件に加えると、作ったほうが早い。

```bash:atcg.bash
#!/bin/bash
set -e
if [ -p /dev/stdin ]; then
    allseq=$(cat -)
else
    allseq=$(cat $1)
fi

echo -e "$allseq" | tr '[a-z]' '[A-Z]' | awk '/^>/{print $0}!/^>/{for(i=1;i<=length;i++){a[substr($0,i,1)]++};n=a["A"]+a["T"]+a["C"]+a["G"];OFS="\t";print a["A"]/n,a["T"]/n,a["C"]/n,a["G"]/n}'
```

最初のif-elseは、標準入力受け取りとファイル受け取りに対応するため。
これをコピペしてファイル名「atcg」で保存して

```bash:bash
sudo ln -s /path/to/atcg /usr/local/bin/
```

とでもしてPATHつなげれば「atcg」コマンドとして動く。

##実行
出力はコマンド名通り、A T C Gの順でタブ区切り出力。
コピペからは

```bash:bash
echo tctgttcttcagaatggataatttctac | atcg
#0.25	0.428571	0.178571	0.142857
```

FASTAからは

```bash:bash
atcg FASTA.fa

#>CHR9:4001761-4001911
#0.306667	0.326667	0.22	0.146667
#>CHR21:45231589-45231739
#0.273333	0.233333	0.243333	0.25
#>CHR3:116878420-116878570
#0.268889	0.217778	0.248889	0.264444
#>CHR16:26967230-26967380
#0.268333	0.205	0.266667	0.26
#>CHR5:155754502-155754652
#0.258667	0.233333	0.253333	0.254667
```

配列名まで大文字になるのはご愛嬌。
bedtools getfasta出力はデフォルトでFASTA形式なので、パイプで同様に行ける。

```bash:bash
bedtools getfasta -fi /path/to/refgenome -bed /path/to/bedfile | atcg
```

全部つなげたければ

```bash:bash
grep -v "^>" FASTA.fa | tr -d '\n' | atcg
#0.258667	0.233333	0.253333	0.254667
```

各場所でそれぞれ出したいとか、Gnuplotでそのまま書きたいとかなら、以下参照。

【ATGC率計算】特定長DNA配列データから各塩基のATGC率を計算する。ヌクレオソーム配列解析など。（ https://qiita.com/Alzt/items/2da327030234c9971520 ）


以上。
Windows10上のSpacemacsでunzipを使う（外部ライブラリへ定義ジャンプしたい）

# 概要

Windows10上のSpacemacsで外部ライブラリに定義ジャンプ ( `Space g g`とか)しようとすると、以下のエラーが出る。

```
apply: Searching for program: No such file or directory, unzip
```

`unzip`なるものが見つからないと言われている。

この手のエラーは、Windowsに該当するパッケージをインストールすると、ふつうは解決する。実際によく似た質問もあった。
[Emacs work with archive. What is the best package?](https://stackoverflow.com/questions/44064716/emacs-work-with-archive-what-is-the-best-package)





# unzipをインストールしたのに見つからない
しかし、MSYS2で `unzip`をインストールしたのに `C:\msys64\mingw64\bin` 下に `unzip`がなかった。

MSYS2で確認してみると、確かにインストールされているはず。

```shell
$ pacman -Ss unzip
mingw32/mingw-w64-i686-perl 5.28.0-1
    A highly capable, feature-rich programming language (mingw-w64)
mingw32/mingw-w64-i686-quazip 0.8.1-1
    C++ wrapper for the Gilles Vollant's ZIP/UNZIP C package (mingw-w64)
mingw64/mingw-w64-x86_64-perl 5.28.0-1
    A highly capable, feature-rich programming language (mingw-w64)
mingw64/mingw-w64-x86_64-quazip 0.8.1-1
    C++ wrapper for the Gilles Vollant's ZIP/UNZIP C package (mingw-w64)
msys/unzip 6.0-2 (compression) [インストール済み]
    Unpacks .zip archives such as those made by PKZIP
```




# パッケージのインストール場所が違っていた
よく見るとpacmanの結果では `msys/unzip`と表示されている。

もしやと思って探すと `C:\msys64\usr\bin`下に `unzip`を見つけた。

Spacemacs側では `C:\msys64\mingw64\bin`のほう (Hunspellとかが入っていた)を実行パスに加えていたので、 `No such file or directory`と言われていた。

これを解決するため、Spacemacsに実行パス `C:\msys64\usr\bin`も指定する。

`.spacemacs` ( `Space f e d`)の `user-init()`内に追記する。

```emacs-lisp
(defun dotspacemacs/user-init ()
  "Initialization for user code:
This function is called immediately after `dotspacemacs/init', before layer
configuration.
It is mostly for variables that should be set before packages are loaded.
If you are unsure, try setting them in `dotspacemacs/user-config' first."

  ;; MSYS2経由でインストールしたパッケージを使う
  (add-to-list 'exec-path "C:\\msys64\\mingw64\\bin")
  (add-to-list 'exec-path "C:\\msys64\\usr\\bin") ; unzipとか
  )
```


あまり関係ないが、「 `exec-path`を追加しろよな！」という話をこちらで見つけて、改めて見直したことが解決の糸口となった。
[How to get emacs Zip-Archive mode to work on Windows](https://stackoverflow.com/questions/872507/how-to-get-emacs-zip-archive-mode-to-work-on-windows)