OmniAICreator/Qiita-1.07M huggingface dataset:
Pythonについて vol07.JSON/CSV(TSV)ファイル読み書き

今回もファイルの読み書きなんですが、JSONとCSV（TSV）についてです。
JSONはAWS SDK for Python（boto3）のinput/outputでよく使います。
TSVはエクセルからコピペして簡単に作れるので、自分は結構好きです。
まぁPythonとエクセルならxlrd/xlwtを使えって話もありますが、それはスルーします。
→ExcelでPythonが使えるようになるという話もありますねぇ。

# JSON
ますJSONライブラリをインポートしてください。

```py
import json
```

JSONの読み込みにはjson.load/json.loadsを使って、書き出しにはjson.dump/json.dumpsを使います。
ファイルを読み書きするときはjson.load/json.dumpを使い、変数（配列・辞書）で読み書きするときはjson.loads/json.dumpsを使います。
https://docs.python.jp/3/library/json.html

## 実装例1
input.jsonというJSON形式のファイルがあるとして、それを読み込みそのままoutput.jsonに書き出します。

```py
import json

with open('input.json', 'r') as f:
    input = json.load(f)

with open('output.json', 'w') as f:
    json.dump(input, f, indent=4)
```

## 実装例2

```py
import json

sample_json1 = {
    'key1' : 'value1',
    'key2' : [
        'value2-1', 'value2-2', 'value2-3'
    ]
}
# これは配列+辞書形式 ≠ JSON形式

sample_json2 = json.dumps(sample_json1, indent=4) # json.dumpsした結果は文字型になります。
print(sample_json2)

sample_json3 = json.loads(sample_json2)
print(sample_json3)
print(sample_json3['key1']) # 辞書型になっているのでkey指定が可能。
print(sample_json3['key2'][1]) 
```

json.dump/json.dumpsでindent=4を入れて見やすいようにしていますが、
中身を見ることがないのであれば要らないです。
上記の実装例2は結果的には、 

```py
sample_json1=sample_json3=json.loads(json.dumps(sample_json1))
```

になっていますが、json.dumpsした時に数字型でも文字型にされてしまうので、イコールにならないこともあります。

→上記の実行結果は以下の通りです。

```py
print(sample_json2)
{
    "key1": "value1",
    "key2": [
        "value2-1",
        "value2-2",
        "value2-3"
    ]
}

print(sample_json3)
{'key1': 'value1', 'key2': ['value2-1', 'value2-2', 'value2-3']}

print(sample_json3['key1'])
value1

print(sample_json3['key2'][1])
value2-2
```

JSONについてはappendixがあります。

# CSV(TSV)
TSV専用のライブラリはなく、CSVライブラリを使ってTSVを読み込みます。
CSVライブラリをインポート(import cvs)したあと、csv.readerでTSVファイルを読み込みます。
https://docs.python.jp/3/library/csv.html

## 実装例
input.tsvファイルを読み込みます。

```py
import csv

with open('input.tsv', 'r') as f:
    input = csv.reader(f, delimiter='\t')
```

デリミタを\t(タブ)にすることでTSVファイルを扱っています。
上記の処理でinputには2次元配列の形でデータが格納されています。
TSV/CSVでファイルを書き出したことがないので省略します。csv.writerやcsv.dictwriterを使うとできます。

もっと言うと、JSONもCSV/TSVもpandasでも扱えます。
import pandas as pdして、pd.read_json/pd.to_jsonとpd.read_csv/pd.to_csvです。（雑
http://pandas.pydata.org/pandas-docs/stable/io.html

# appendix
PythonのAWS CLIを使ったとき、responseがJSON形式っぽいやつで返ってきます。
ただこの中に日付型のデータがあるためなかなか扱いが面倒です。
（JSONには日付型はないのが、っぽいと言っている所以です。）

そのために以下のような関数を作って、ダンプする前に文字列に変換します。

```py
def json_serial(obj):
    # 日付型の場合には、文字列に変換します
    if isinstance(obj, (datetime, date)):
        return obj.isoformat()
    # 上記以外はサポート対象外.
    raise TypeError ("Type %s not serializable" % type(obj))

response = hogehoge() # AWS CLI

with open('result.json', 'w') as f:
    json.dump(response, f, default=json_serial, indent=4)
```

isinstanceでdatetime型かdate型なのかを確認して、isoformatで決められたフォーマットで文字列に変換しています。めんどいですね。
この関数(json_serial)はどこからか拾ってきました。
[[Python] dateやdatetimeをjson.dumpでエラーなく出力する](https://www.yoheim.net/blog.php?q=20170703)
たぶんここ。
Android の ConstraintLayout で特定ウィジェットの中心を軸に高さの異なるウィジェットを並列配置してみた件

# 方法

ウィジェット A の中央を軸に配置したいウィジェット B にウィジェット A の ID を指定した `layout_constraintTop_toTopOf` と `layout_constraintBottom_toBottomOf` を設定します。

# サンプル

[ImageView](https://developer.android.com/reference/android/widget/ImageView) の中心を軸にして [TextView](https://developer.android.com/reference/android/widget/TextView) と [Button](https://developer.android.com/reference/android/widget/Button) を横並びに設置します。

## コード

``` activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">

    <android.support.constraint.ConstraintLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:padding="8dp">

        <android.support.v7.widget.AppCompatImageView
            android:id="@+id/image_view"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:src="@mipmap/ic_launcher_round"
            app:layout_constraintEnd_toStartOf="@id/text_view"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toTopOf="parent" />

        <android.support.v7.widget.AppCompatTextView
            android:id="@+id/text_view"
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:padding="8dp"
            android:text="フェアプレー・ポイントを差し上げます ⚽️"
            android:textAppearance="?android:attr/textAppearanceMedium"
            app:layout_constraintBottom_toBottomOf="@id/image_view"
            app:layout_constraintEnd_toStartOf="@+id/button"
            app:layout_constraintStart_toEndOf="@id/image_view"
            app:layout_constraintTop_toTopOf="@id/image_view" />

        <android.support.v7.widget.AppCompatButton
            android:id="@id/button"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="送信"
            app:layout_constraintBottom_toBottomOf="@id/image_view"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintStart_toEndOf="@id/text_view"
            app:layout_constraintTop_toTopOf="@id/image_view" />
    </android.support.constraint.ConstraintLayout>
</layout>
```

## 結果

![Screenshot_1532239102.png](https://qiita-image-store.s3.amazonaws.com/0/6881/3adeea04-a956-0b00-66af-b8a5889d3ed3.png)

# 関連記事

- https://qiita.com/84d010m08/items/9abbd327c55fb81a9219
Pythonについて vol06.ファイル読み書き

今回はファイルの読み込みと書込みをやります。
とりあえず単純なものだけ扱います。JSON、CVS(TVS)については次回の予定です。

# 読み込み

```py
with open(<file path>, 'r') as f:
    data = f.readlines()
```

とやります。fileをr(読み込みモード)で開いています。
ファイルの中身の代入はreadとreadlineもありますが、はじめはreadlinesだけ覚えておけば良いと思います。
上記の例ではdataにfileの中身が1行づつ配列として格納されます。

# 書き込み

```py
with open(<file path>, 'w') as f:
    f.write(’書込みしたい文字列’)
```

とやります。fileをw(上書きモード)で開いています。aだと追記モードです。
文字列に改行コードが含まれていない場合は、ファイルで改行されません。
また文字列配列を代入するときは、

```py
with open(<file path>, 'w') as f:
    f.writelines(書込みしたい文字列配列)
```

とします。こちらも先ほど同様改行コードがないと、ファイルで改行されません。

またopenは以下のようにも書けますが、
closeし忘れを防止するためにwithを使うのが良いです。

```py
f = open(<file path>, 'r')
date = f.readlines()
f.close()
```
vmesxiのホストをドメイン参加させると「失敗 - このホストには適切な FQDN がありません。 」のエラーが発生する

vmesxiの管理コンソールからドメイン名を入力した、管理者IDとパスワードを入力してドメイン参加を試みると
`失敗 - このホストには適切な FQDN がありません。`
のエラーが発生する

色々と調べた所
ホスト名がlocalhostとなっていた事が原因

ホスト名をDNSに登録したホスト名に変更後、
再度、ドメイン参加を試みた所、エラーが発生する事なく成功した。
Facebookのシェア数を取得する方法

Facebook Graph API（ver.3.0）の使い方がいまいちふわっとしているので、メモと備忘録をかねてシェア数を取得するまでの手順を書きました。
仕様が常に新しくなるので、今回書いた方法では取得できなくなるかもしれません。
最新情報については[公式ドキュメント](https://developers.facebook.com/docs/graph-api/)をご参考ください。
もし、間違い等ありましたら、ご指摘いただけると幸いです。

## Facebookアプリをつくる
https://developers.facebook.com/ にログインしてアプリをつくります。
詳しくはこちら → [アプリの登録と構成](https://developers.facebook.com/docs/apps/register?locale=ja_JP)


## アプリを認証する
ブラウザで次のURLにアクセスしてください。

```
https://www.facebook.com/dialog/oauth?client_id={アプリID}&redirect_uri={アプリドメイン}
```
{アプリID}と{アプリドメイン}はアプリの詳細画面の「設定>ベーシック」から確認できます。
成功すると、 `https://sample.com/?code=XXX`というようなURLに飛ばされます。
**?code=**の後の英数字が認証コードです。

※ 「URLを読み込めません: このURLのドメインはアプリのドメインに含まれていません。このURLを読み込むには、アプリ設定のアプリドメインにすべてのドメインとサブドメインを追加してください」のエラーが出る場合は**クライアントOauth**を設定してください。
![app.png](https://qiita-image-store.s3.amazonaws.com/0/13307/060a04e9-85a8-01d2-23fc-0236f662a92f.png)

## アクセストークンを取得する
ブラウザで次のURLにアクセスしてください。

```
https://graph.facebook.com/oauth/access_token?client_id={アプリID}&client_secret={app_secret}&grant_type=client_credentials
```
成功すると次のようなjsonデータが返ってきます。

```json
{
  "access_token": "**************************************************",
  "token_type": "bearer"
}
```


### いいね数・シェア数を取得する
上記で取得したアクセストークンを使って、ブラウザで次のURLにアクセスしてください。

```
https://graph.facebook.com/?id={いいね数・シェア数を取得したいサイトのURL}&fields=og_object{engagement},engagement&access_token={access_token}
```
このURLにアクセスするとシェア数が取得できます。



## 参考サイト
- [「SNS Count Cache 0.11.1」でFacebookのシェア数をカウントする方法【WordPress】](https://www.islog.jp/entry/sns-count-cache-facebook/)
- [[Facebook Graph API]無期限のアクセストークンの取得方法](https://qiita.com/xiushu53/items/f2d699704d7325d02169)
[Numpy] 2つのndarrayを比較する

### はじめに

各インデックスにおいて1から9までの値をランダムに持つ大きさ100のndarrayを2つ生成してみる。

```python
>>> import numpy as np

>>> a = np.random.randint(1, 10, 100)
>>> b = np.random.randint(1, 10, 100)

>>> a
array([3, 4, 7, 1, 6, 6, 9, 7, 7, 8, 9, 7, 9, 3, 5, 4, 6, 3, 5, 8, 3, 2,
       9, 7, 7, 6, 1, 1, 2, 2, 8, 7, 1, 7, 1, 2, 9, 3, 3, 1, 6, 3, 3, 9,
       1, 8, 7, 4, 3, 8, 5, 5, 6, 2, 7, 8, 3, 2, 9, 4, 6, 7, 1, 9, 3, 9,
       8, 3, 4, 5, 9, 1, 4, 1, 6, 1, 6, 1, 1, 3, 2, 6, 8, 1, 1, 6, 5, 5,
       5, 7, 9, 9, 3, 1, 2, 4, 6, 9, 6, 2])
>>> b
array([1, 1, 9, 5, 5, 3, 3, 4, 8, 4, 6, 1, 5, 3, 1, 1, 9, 6, 8, 8, 1, 2,
       7, 6, 2, 5, 5, 2, 7, 8, 1, 3, 4, 9, 1, 2, 8, 5, 6, 9, 9, 3, 6, 4,
       9, 6, 2, 5, 4, 2, 9, 6, 2, 2, 9, 9, 5, 4, 3, 1, 9, 2, 2, 6, 2, 7,
       4, 2, 3, 2, 6, 5, 1, 2, 8, 4, 2, 4, 8, 5, 7, 4, 2, 6, 7, 7, 9, 1,
       2, 8, 8, 9, 1, 7, 5, 4, 4, 9, 7, 7])
```

今回は、この2つのndarrayを比較して、**値が等しくなっているインデックスの個数**および**値が等しくなっているインデックスの値**を取得してみようと思う。

### `==`を使って2つのndarrayを比較したときの返り値について

実際に `a == b`としてみると、

```python
>>> a == b
array([False, False, False, False, False, False, False, False, False,
       False, False, False, False,  True, False, False, False, False,
       False,  True, False,  True, False, False, False, False, False,
       False, False, False, False, False, False, False,  True,  True,
       False, False, False, False, False,  True, False, False, False,
       False, False, False, False, False, False, False, False,  True,
       False, False, False, False, False, False, False, False, False,
       False, False, False, False, False, False, False, False, False,
       False, False, False, False, False, False, False, False, False,
       False, False, False, False, False, False, False, False, False,
       False,  True, False, False, False,  True, False,  True, False,
       False])

>>> type(a == b)
<class 'numpy.ndarray'>
```

このように値が等しいところは`True`、値が異なるところには`False`が入ったndarrayが返ってきていることがわかる。
このndararyをうまく使って、**値が等しくなっているインデックスの個数**および**値が等しくなっているインデックスの値**を取得することができる。

###  `np.sum()`を使って値が等しくなっているインデックスの個数を取得

通常、`np.sum()`を使用すると、引数として与えられたndarrayのすべての要素の合計値が出力される。

```python
>>> c = np.array([1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
>>> np.sum(c)
55
```

今回のポイントは、**Falseは0、Trueは1**として評価されることである。つまり、前述の`a == b`を`np.sum()`の引数として与えると、Trueの数が返されるのである。

```python
>>> np.sum(a == b)
10
```
今回、2つのndarrayにおいて**10個**のインデックスが同一の値を持っていることがわかった。

###  `np.where()`を使って値が等しくなっているインデックスの値を取得

`np.where()`を使うと、引数として与えられた条件を満たすインデックスが返される。
**Falseは0、Trueは1**として評価されることを思い出すと、

```python
>>> np.where((a == b) == 1)
(array([13, 19, 21, 34, 35, 41, 53, 91, 95, 97]),)
```

こんな感じに書けることがわかる。

ちなみに、一発で`np.where(a == b)`でも良い。

```python
>>> np.where(a == b)
(array([13, 19, 21, 34, 35, 41, 53, 91, 95, 97]),)
```


実際に、得られたindexにおける2つのndarrayの値を見てみると、

```python
>>> for i in np.where((a == b) == 1)[0]:
...     print(a[i], b[i])
... 
3 3
8 8
2 2
1 1
2 2
3 3
2 2
9 9
4 4
9 9
```

確かに同じ値になっていることが確認できる。またその数は10個で`np.sum()`を使って求めた個数にも一致していることが確認できた。

### おわりに
たとえば`a == b`のところを `a > b`にしたりするとaがbよりも大きい値を持っているインデックスの個数、値を取得できたりといろいろ応用が効く。numpyは便利。
Google Container Registryのお掃除ツールを作ってみた

# はじめに
Google Container Registryにおいて、適当に並列化してイメージ削除するようなツール作ってみました。

https://github.com/h-r-k-matsumoto/gcr-garbage-collect

# 経緯
Google Container Registryでタグ無しの不要なイメージを精神衛生上消したいな…と思った時、コンソール画面から行うと・・・。

10件以上まとめて行うとほぼ確実に、下記のように
 **1つ以上の選択したイメージを削除できませんでした。**
と表示されていくつかの削除に失敗します。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/268550/954f1a4e-a303-5427-3618-8d4bdeb45253.png)

じゃあシェルから下記のように実行すると、安定して削除できるけれども1つのイメージ削除に、5秒くらいかかり、 **ものすごく遅い。**

```
# get image list 
gcloud container images list-tags asia.gcr.io/{project-id}/${image-name}  --filter="NOT tags:* AND timestamp.datetime < '2018-06-01'"

# delete image
gcloud container images delete asia.gcr.io/{project-id}/${image-name}@sha256:{digest} --force-delete-tags  --quiet
```

それじゃ並列化して削除すればいいじゃん！って事でツール作ってみました。

# ツール

## できたもの

https://github.com/h-r-k-matsumoto/gcr-garbage-collect

**削除対象の確認**

```
$ java -jar gcr-garbage-collect-0.0.1-SNAPSHOT.jar --dry-run=true
```

**削除実行**

```
$ java -jar gcr-garbage-collect-0.0.1-SNAPSHOT.jar --dry-run=false
```

**特定のイメージだけ削除**

```
java -jar gcr-garbage-collect-0.0.1-SNAPSHOT.jar --gcloud.container.image=asia.gcr.io/{gcp-project-id}/{image-name}
```

**並列数の変更**

```
$ java -jar gcr-garbage-collect-0.0.1-SNAPSHOT.jar --parallelism=16
```


## 作成に関して

- container registryに対するAPIが、[Googleドキュメント](https://cloud.google.com/java/apis)見てもない…。仕方がないのでgcloud直接実行形式にしてます。
- windows環境では、application.yaml、もしくは実行時引数として<br> 　`--gcloud.command="C:/Program Files (x86)/Google/Cloud SDK/google-cloud-sdk/bin/gcloud.cmd"` <br>等指定してください。

## その他

- 久々にProcessBuilder使ったけど、OS毎による `<` や、`"` の扱い、やっぱ吸収してくれないのね。
- docker image化しようと思ったけど、gcloudの認証周りめんどくさいし、やめました。
- どれくらい早くなったかなーと思って比較しようと思いましたが、そもそも速度図っていないのでやめました。
- 精神衛生上だけの問題で削除してます。別に古いのが残っていたとしてもたいして実害無いです。(GCSの料金も気になるほどじゃないです )
在MacBook Air 上安装Scrapy时的使用命令


pip install --upgrade setuptools
sudo -H pip install incremental==16.10.1
sudo -H pip install --upgrade pip
sudo -H pip install scrapy

Python:使用代理proxy爬虫
http://gohom.win/2016/01/21/proxy-py/

HTTPS代理IP
http://www.xicidaili.com/wn/


基本上程序是一直运行的只在特定的情况下停止的实现方式
－－－－－－－－－参考
import os
print os.getpid()
上記で、プロセスIDが取得出来ます。
Linux等であれば、「kill -9 プロセスID」で強制終了できます。
getpid()の値をファイルに出力していれば、「kill -9 `cat ファイル名`」で可能です。

－－－－－－－－－－实现
程序运行最初将pid写入文件里面，执行时判断pid是否变化，只在想要停止的时候手动改变pid，
则程序就会自动停止
－－－－－－－－－－
AlibabaCloudのRAMグループを活用する

# はじめに
前回は、AlibabaCloudのRAMユーザーを作成しました。
今回は、RAMグループについて触れます。

# ドキュメントはこちら

[ユーザーグループの管理 - ユーザーガイド| Alibaba Cloud ドキュメントセンター](https://jp.alibabacloud.com/help/doc-detail/28648.html?spm=a2c5t.11065259.1996646101.searchclickresult.74577483tWs9Fb)

> Alibaba Cloud アカウントで多数の RAM ユーザー を作成した場合は、ユーザーとその権限を管理しやすくするために、グループ単位でユーザーを管理することをお勧めします。

とあります。

# RAMグループで管理するその理由とは？

例えば、会社から一人退職したとします。
その退職者に渡したRAMユーザーを消すことがあると思います。
RAMユーザーを消すとその権限ポリシーも消えます。
さて、その権限はどうだったでしょうか？
消えたポリシーは復活できません。

どこかのドキュメントに残したり
履歴管理するなどの運用だと大変になります。

そういった場合のために
グループに権限ポリシーを付与し
グループにユーザーを含めるようにします。

outsourcingグループにsuzuki, yamadaユーザーを追加します。外注契約が終わったあとに、yamadaユーザーを削除する。外注パートナーの権限はひとつに管理して
引き続き使えるようにする感じです。

RAMグループ、outsourcing
┗RAMユーザー、suzuki
┗RAMユーザー、yamada

↓

RAMグループ、outsourcing
┗RAMユーザー、suzuki

# コンソールから作成する
[AlibabaCloudのRAMユーザーを作ってみる](https://qiita.com/wa-ta-ru/items/ab4dacc67d787e0739fa)
のときの、shinya-furuwataをグループに追加して権限を付与してみます。
shinya-furuwataの権限は外しておきます。

## RAM(Resource Access Managment)を選択

![9423eb6b.png](https://qiita-image-store.s3.amazonaws.com/0/241104/b64d4f9b-5b9b-ae3c-9b48-4ef490422545.png)

## RAMグループを作成します

![e6c8092c.png](https://qiita-image-store.s3.amazonaws.com/0/241104/25ea79e8-3694-2cb8-010c-aad5791868f2.png)

![cfd7b60b.png](https://qiita-image-store.s3.amazonaws.com/0/241104/dae052a5-998f-f424-1249-5dcc7f8d8d27.png)

OKを押すと、グループが作成されます。
AlibabaCloud検証のためのグループを作成しました。

## RAMグループに権限を付与します。

![321d8e3a.png](https://qiita-image-store.s3.amazonaws.com/0/241104/fb1d12f0-82bf-9dd8-8491-53d8b635ec09.png)

![e0f37690.png](https://qiita-image-store.s3.amazonaws.com/0/241104/20f791ce-fef5-4bd0-3640-b262efe3efeb.png)

AlibabaCloud検証のためのグループに
AdministratorAccess権限を付与しました。

## RAMグループとRAMユーザーを関連付けします

![ad2744cc.png](https://qiita-image-store.s3.amazonaws.com/0/241104/330b5dae-2e52-4273-f840-fe2cd00a1802.png)

![711f80c1.png](https://qiita-image-store.s3.amazonaws.com/0/241104/76059abe-8a3d-8b63-aede-941a00843a9f.png)

shinya-furuwataユーザー
AlibabaCloud検証のためのグループに入れました。

# まとめ
個人利用ではあまり意識しませんが
会社や業務であれば、事業部や担当などで区分けした方がいいでしょう。
ユーザーは、作成し更新も削除もあります。
その都度同じ権限や権限の管理を一人一人の名前で管理するなど大変です。グループを活用することで、負担を減らしましょう。
Swift：n番目を先頭としたループになるような配列ソート

#はじめに
`[A, B, C, D, E, F, G]`を`[C, D, E, F, G, A, B]`のようにn番目を先頭にして、全体としてはループしているような配列を取得したい場合があったため、方法を考えた．

#方法
```swift:
let array = ["A", "B", "C", "D", "E", "F", "G"]

let n: Int = 3
let newArray = Array(d.dropFirst(n)) + Array(d.prefix(n))

Swift.print(newArray) // -> ["D", "E", "F", "G", "A", "B", "C"]
```
こんな感じ
[Elm] 危険🐐img onerror芸

本記事では、The Elm Architecture を容易に破壊しうる闇の技術「img onerror芸」をご紹介します。
原則として「img onerror芸」は使わないに越したことはないですが、[危険🐐スクリプト芸](https://qiita.com/arowM/items/93201dd5aded6e264e19)のように、ごくまれにメリットがデメリットを上回る場合があるかもしれません。

「危険🐐スクリプト芸」と同じく基本的に飛び道具的な内容のため、乱用は絶対にさけましょう。
The Elm Architecture の脆弱性をついたような技法なので何が起きても知りません。
以下の内容はバージョン0.18 を想定しています。

## img onerror 芸とは

XSS脆弱性をつくときによく使われる

```html
<img src="1" onerror="alert(1)">
```

を悪用した非推奨テクニックです。

念のため上記のHTMLを説明しておくと、`img` タグの `src` に存在しないパスを設定することで意図的に `onerror` を発火させ、任意のJSを実行する手法です。

では、Elmで以下のようなViewを作成するとどうなるでしょうか？

```elm
{-| An evil view that sends `Msg` on rendering.
-}
onRenderThis : msg -> Html msg
onRenderThis msg =
    Html.img
        [ Attributes.src ""
        , Events.on "error" <| Json.succeed msg
        ]
        []
```

上記のテクニックと同じように、この `img` タグが画面上に描画された瞬間に `Events.on "error"` の部分が発火するため、
「あるViewが実際に画面に描画された瞬間に任意の `Msg` を飛ばして `update` 関数を実行する」というハックが可能になります。

The Elm Architecture をこわすので絶対にやらない方が良いですね。
Elm 0.23 くらいで使用禁止になるかもしれません。

[elm-evil-sendmsg](http://package.elm-lang.org/packages/arowM/elm-evil-sendmsg/latest) というライブラリになっているので、どうしても使いたいときにはこれを使うとお手軽でいいでしょう。

## つかいどころ

もう一度言います。 使うべきではありません。
ちょっとだけ便利になるかもしれないパターンは、たとえば以下のようなユースケースでしょうか？

### 特定のDOMに対して `port` でJSのコードを適用したい場合

[DOM更新後にJSを実行する方法](https://qiita.com/arowM/items/ff98bce79a7080cbb38a) がちゃんと用意されているのでこちらを使いましょう。
でも、DOMを作成するタイミングがあまりにも複雑で、`update` 関数のどこでそのDOMを作成するかがわかりにくい場合、img onerror芸を使うとちょっとすっきりします。
でも、すっきりするだけでそんなバッドハックを使ったらダメです。
`update` 関数の書き方を工夫すればいくらでもすっきり書けるはずです。

### Model の値を監視する

[Evil.SendMsg.when](http://package.elm-lang.org/packages/arowM/elm-evil-sendmsg/1.0.0/Evil-SendMsg#when) を使えば、Modelの特定の値を監視して、閾値を超えたら Msg を発行するような実装が可能になります。

[elm-evil-sendmsgのデモ](https://arowm.github.io/elm-evil-sendmsg/)では、さくらちゃんがデレる閾値の検出に `Evil.SendMsg.when` を利用しています。

でも、`update` 関数で常に対象の値をチェックしたら同じことができます。
ちょっと簡単になるからってこんなバッドハックを使ったらダメです。

### ボタンを押す処理を代替する

[elm-evil-sendmsgのデモ](https://arowm.github.io/elm-evil-sendmsg/)では、さくらちゃんとの会話を進めるために「Click to Next」のボタンを押す必要がありますが、「Auto」ボタンを押すと自動で会話が進んでいきます。
この挙動を

* ユーザーの行動によって Msg を発行するボタン
* 画面に表示された瞬間に Msg を発行するボタン

と抽象化して考えるととてもすっきり実装できます。

でも、これも本当は `update` 関数で会話を進めるときに Auto ボタンが押されているかチェックして動作を分岐させるのが正しいやり方です。
「抽象化できてるオレかっけー」と思ってバッドハックを使うのはダメです。


[![sakura.jpg](https://qiita-image-store.s3.amazonaws.com/0/16345/aac3b4a7-06c3-b950-2852-dae67665454f.jpeg)](https://twitter.com/hashtag/%E3%81%95%E3%81%8F%E3%82%89%E3%81%A1%E3%82%83%E3%82%93%E6%97%A5%E8%A8%98?src=hash)
[さくらちゃんにご飯をあげる](https://www.amazon.co.jp/gp/registry/wishlist/20ZV2VC57615B/ref=nav_wishlist_lists_1)
PythonでAM音響信号の変動強度とラフネスを検証

# AM音（周期的振幅変調音）とは

振幅が周期的に変化する音。以下のような数式および波形で表せます。
（ $f_c$:搬送周波数、$f_{mod}$: 変調周波数）

```math
AM(t) = A\lbrace1 + A_m\cos(2\pi f_{mod}t)\rbrace\cos(2\pi f_ct)\\
= A\lbrace cos(2\pi f_ct) + \frac{1}{2}A_m\cos\lbrack 2\pi (f_c - f_{mod})t\rbrack + \frac{1}{2}A_m\cos\lbrack 2\pi (f_c + f_{mod})t\rbrack \rbrace\
```
![AM.png](https://qiita-image-store.s3.amazonaws.com/0/231777/64e064be-0827-e16f-f06b-a5c7162cc10e.png)



# 実装
早速Pythonで実装してみます。

```python:AM.py
import numpy as np
import matplotlib.pyplot as plt
import soundfile as sf

fs = 48000
t = 3

n = np.arange(t * fs)

#変調周波数
fmod = 20
#搬送周波数
fc = 500

#振幅
A = 1
Am = 3
#周期的振幅変調音
AM = A * (1 + Am * np.cos(2*np.pi*fc*n/fs) + 1/2 * Am*np.cos(2*np.pi*(fc-fmod)*n/fs) + 1/2 * Am*np.cos(2*np.pi*(fc+fmod)*n/fs))

plt.plot(n / fs, AM, label='fmod=200[Hz], fc=500[Hz]')
plt.xlabel('time[s]')
plt.xlim(0, 0.1)
plt.legend(loc='lower right')
plt.show()
plt.savefig("AM.png",format = 'png', dpi=300)
sf.write("AM.wav", AM, fs)
```

# 変動強度とラフネス
人間は5Hz以下の変調周波数においては物理的に追従できますが、20Hzくらいになってくると時々刻々の変動には追従できなくなります。
低い変調周波数のときに感じられる変動感のことを**変動強度**といい、高い変調周波数のときに感じられる変動感のことを**ラフネス**といいます。

$f_{mod} = 4\ \mathrm{[Hz]},\ f_{c} = 500\ \mathrm{[Hz]}$の音
https://www.dropbox.com/s/khdbt4saebgbsxz/AM_4_500.wav?dl=0
はっきりウワンウワンなっているのがわかります。ちなみに変動強度は$f_{mod} = 4\ \mathrm{[Hz]}$のとき最大だそうです。

$f_{mod} = 20\ \mathrm{[Hz]},\ f_{c} = 500\ \mathrm{[Hz]}$の音
https://www.dropbox.com/s/4z2cwcwlexsba2q/AM_20_500.wav?dl=0
ウワンウワンというよりはズバババって感じですね（語彙）。これがラフネスという感覚なのでしょうか。

変調周波数を挙げていくとラフネスが最大になり、それを超えるとラフネスが消失します。

$f_{mod} = 150\ \mathrm{[Hz]},\ f_{c} = 500\ \mathrm{[Hz]}$の音
https://www.dropbox.com/s/a7rdtsp3d2b79yr/AM_150_500.wav?dl=0
ものすごくザラザラした印象を受けます。

$f_{mod} = 300\ \mathrm{[Hz]},\ f_{c} = 500\ \mathrm{[Hz]}$の音
https://www.dropbox.com/s/gpy9sd3j3saeky2/AM_300_500.wav?dl=0
ブーって感じですが、確かにザラザラ感はなくなっています。

ラフネスの消失境界は臨界帯域(参照リンクhttps://www15.atwiki.jp/ad06/pages/76.html)
によって規定されており、1kHz以下のの搬送周波数では変調周波数が臨界帯域幅を超えると側波成分（$\frac{1}{2}A_m\cos\lbrack 2\pi (f_c - f_{mod})t\rbrack + \frac{1}{2}A_m\cos\lbrack 2\pi (f_c + f_{mod})t\rbrack $の部分）聴覚フィルタ内の干渉がおきなくなるため、ラフネスを感じなくなります。

ところが、搬送周波数が2kHzを超えると臨界帯域幅にかかわらず250Hz以上の変調周波数でラフネスが消失します。250Hzは周期的な変動の時間分解能であると考えられており、これより変調周波数が高くなると変動を知覚できなくなるためです。

$f_{mod} = 300\ \mathrm{[Hz]},\ f_{c} = 2500\ \mathrm{[Hz]}$の音
https://www.dropbox.com/s/j8ab31q3obgdrf6/AM_300_2500.wav?dl=0
確かにあまりザラザラ感はありませんね。

2kHz以上の搬送周波数では変動周波数が40~70Hzでラフネスが最大になります。
$f_{mod} = 50\ \mathrm{[Hz]},\ f_{c} = 2500\ \mathrm{[Hz]}$の音
https://www.dropbox.com/s/j8ab31q3obgdrf6/AM_300_2500.wav?dl=0
ものすごくカオスな音になりました。

# 参考文献
[1] 岩宮眞一郎. 図解入門 よくわかる最新音響の基本と応用. 秀和システム, 2011 年.
[WIP]Goを仕事で書き始める前に読んでおくといいドキュメント

Goを仕事で書き始める前に読んでおくとよかったドキュメント集をまとめていく

#　参照ドキュメント一覧
- [Effective Go](https://golang.org/doc/effective_go.html)
- [Go Code Review Comments](https://github.com/golang/go/wiki/CodeReviewComments#comment-sentences)
- etc

### コメントの書き方
#### 参照ドキュメント
- [CodeReviewComments#comment-sentences](https://github.com/golang/go/wiki/CodeReviewComments#comment-sentences)
- [Effective Go #Commentary](https://golang.org/doc/effective_go.html#commentary)

#### 内容メモ
- GoはC-styleの`/* */`のブロックコメントとC++-styleの`//`のラインコメントをコメントの仕方として提供している
- ブロックコメントは主にパッケージコメントとして使われる
- すべてのパッケージはパッケージコメントを書くべき
- plain textで書く、
- コメントはコメント対象のものの名前から始める
- コメントはフルセンテンスで書くべき、最後はピリオド（`.`）で終わるべき
【Swift】使いこなせば便利？〜再帰的列挙型〜

# これは？
みなさんはSwiftの **再帰的列挙型** というものをご存知でしょうか。

本稿では、意外と知られていない **再帰的列挙型** の使い方について説明します。

# 再帰的列挙型とは？
再帰的列挙型とは、 **associated value** としてその列挙型自身を再帰的に持つ列挙型のことです。

言葉だけではわかりにくいので、実際に例を示します。

```swift
enum ArithmeticExpression {
    case number(Int)
    indirect case addition(ArithmeticExpression, ArithmeticExpression)
    indirect case multiplication(ArithmeticExpression, ArithmeticExpression)
}
```

上記のプログラムは、単純な演算を行うための再帰的列挙型の定義です。

一つ目のケースはInt型を **associated value** として持ちます。
演算のために使う被演算子の定義です。

二つ目と三つ目のケースはそれぞれ加算と乗算の定義です。
そしてどちらも `ArithmeticExpression` 自身を **associated value** として持ちます。
このような場合、caseの前に **indirect修飾子** を付加します。

# 活用例
例えば、この `ArithmeticExpression` を利用して、 `(5 + 4) * 2` という演算を処理してみましょう。

```swift
let five = ArithmeticExpression.number(5)
let four = ArithmeticExpression.number(4)
let two = ArithmeticExpression.number(2)
let sum = ArithmeticExpression.addition(five, four)
let product = ArithmeticExpression.multiplication(sum, two)
```

上記のプログラムは以下のような定義となります。

- `ArithmeticExpression` の `number` として `five` を初期化
- `ArithmeticExpression` の `number` として `four` を初期化
- `ArithmeticExpression` の `number` として `two` を初期化
- `ArithmeticExpression` の `addition` として `five` と `four` を被演算子に指定して `sum` を初期化
- `ArithmeticExpression` の `multiplication` として `sum` と `two` を被演算子に指定して `product` を初期化

さて、これで演算を行う準備が整いました。
変数 `product` は `(5 + 4) * 2` の演算を `ArithmeticExpression` として持つことになります。

あとはこの `ArithmeticExpression` を引数に取る評価関数を定義します。

```swift
func evaluate(_ expression: ArithmeticExpression) -> Int {
    switch expression {
    case let .number(value):
        return value
    case let .addition(left, right):
        return evaluate(left) + evaluate(right)
    case let .multiplication(left, right):
        return evaluate(left) * evaluate(right)
    }
}

print(evaluate(product))
// Prints "18"
```

上記の `evaluate` 関数は以下のような定義となります。

1. ArithmeticExpressionを引数として受け取る
2. switch文でケースを分岐する
  - .numberならば: その **associated value** であるInt型を返す
  - .additionならば: 2つの被演算子をそれぞれ `evaluate` 関数に引数として渡してその結果を加算する
  - .multiplicationならば: 2つの被演算子をそれぞれ `evaluate` 関数に引数として渡してその結果を乗算する

この関数 `evaluate` に `product` を引数として渡すと、その演算結果である `18` が返ってきます。

このように、再帰的列挙型は再帰関数とともに扱うことで非常に直感的なコーディングが可能になります。

# 参考
[Apple Inc. “The Swift Programming Language" -Enumerations](https://docs.swift.org/swift-book/LanguageGuide/Enumerations.html)
chrony導入メモ@Debian8

Debian 8にそれっぽい感じでChronyをインストールする際の設定を紹介します．完全に個人的な備忘録です．Debian 8なのは，OpenBlocks 600Dがまだ現役だから．

pool directiveを使えばスマートにかけますが，Debian 8では，v1.30でpool directiveが使えません．残念．

```bash
# dpkg -l | grep chrony
ii  chrony                           1.30-2+deb8u1             powerpc      Set the computer clock from time servers on the Net
```

以下インストール手順．

```bash:インストール
apt install chrony
cp /etc/chrony/chrony.conf /etc/chrony/chrony.conf.orig
vim /etc/chrony/chrony.conf
diff -u  --to-file=/etc/chrony/chrony.conf /etc/chrony/chrony.conf.orig
service chrony restart
```

コンフィグは以下．

```diff:/etc/chrony/chrony.conf
--- /etc/chrony/chrony.conf.orig        2016-05-10 01:02:04.684764657 +0900
+++ /etc/chrony/chrony.conf     2016-05-10 01:08:58.000000000 +0900
@@ -17,11 +17,46 @@
 # fails they will be discarded.  Thus under some circumstances it is
 # better to use IP numbers than host names.

-server 0.debian.pool.ntp.org offline minpoll 8
-server 1.debian.pool.ntp.org offline minpoll 8
-server 2.debian.pool.ntp.org offline minpoll 8
-server 3.debian.pool.ntp.org offline minpoll 8
+# server 0.debian.pool.ntp.org offline minpoll 8
+# server 1.debian.pool.ntp.org offline minpoll 8
+# server 2.debian.pool.ntp.org offline minpoll 8
+# server 3.debian.pool.ntp.org offline minpoll 8

+# option iburst, prefer: version 1.25
+# pool directive: version 2.00
+
+# nict
+#pool ntp.nict.jp prefer minpoll 6 maxpoll 10
+server ntp.nict.jp iburst prefer minpoll 6 maxpoll 10
+server ntp.nict.jp iburst prefer minpoll 6 maxpoll 10
+server ntp.nict.jp iburst prefer minpoll 6 maxpoll 10
+
+# mfeed
+#pool ntp.jst.mfeed.ad.jp prefer iburst minpoll 6 maxpoll 10
+server ntp1.jst.mfeed.ad.jp iburst minpoll 6 maxpoll 10
+server ntp2.jst.mfeed.ad.jp iburst minpoll 6 maxpoll 10
+server ntp3.jst.mfeed.ad.jp iburst minpoll 6 maxpoll 10
+
+# OCN
+server ntp-tk01.ocn.ad.jp iburst prefer minpoll 6 maxpoll 10
+server ntp-tk02.ocn.ad.jp iburst prefer minpoll 6 maxpoll 10
+
+# pool.ntp.org
+#pool jp.pool.ntp.org iburst minpoll 6 maxpoll 10
+#pool 0.jp.pool.ntp.org minpoll 6 maxpoll 10
+#pool 1.jp.pool.ntp.org minpoll 6 maxpoll 10
+#pool 2.jp.pool.ntp.org minpoll 6 maxpoll 10
+#pool 3.jp.pool.ntp.org minpoll 6 maxpoll 10
+server 0.jp.pool.ntp.org iburst minpoll 6 maxpoll 10
+server 1.jp.pool.ntp.org iburst minpoll 6 maxpoll 10
+server 2.jp.pool.ntp.org iburst minpoll 6 maxpoll 10
+server 3.jp.pool.ntp.org iburst minpoll 6 maxpoll 10
+
+# ring
+#pool ntp.ring.gr.jp iburst minpoll 6 maxpoll 10
+#server ntp0.ring.gr.jp iburst minpoll 6 maxpoll 10
+#server ntp1.ring.gr.jp iburst minpoll 6 maxpoll 10
+#server ntp2.ring.gr.jp iburst minpoll 6 maxpoll 10

 # Look here for the admin password needed for chronyc.  The initial
 # password is generated by a random process at install time.  You may
```

```
allow 192.168.11.0/24
local stratum 10
```

サービスを有効にして，同期状況を確認する．

```sh
systemctl enable chrony
insserv -s | grep chrony
chronyc sources
chronyc tracking
rtcfile /var/lib/chrony/rtc
rtcsync
```

* [13.3. chrony の使用](https://access.redhat.com/documentation/ja-JP/Red_Hat_Enterprise_Linux/7/html/System_Administrators_Guide/sect-Using_chrony.html)
Rails tutorial    Git push できない　エラーについて

Rails  tutorial 第1章、第2章で


公開鍵設定して、チュートリアル通り、bitbucket に登録したのに

remote add の後のgit push が できない！！


というエラーにハマりました。
　



The authenticity of host 'bitbucket.org (104.192.143.1)' can't be established.

　


？？？
　


どうやら、bitbucket  のRead me ファイルが原因だったみたいです。

レポジトリを新しく作るときに、デフォルトで、Read me ファイルを　
作るがYes

になってます。これを、No にしてください！！
VisualStudioCodeでmarkdownをHTMLにしたり、PDFにしたりする

# VisualStudioCodeはいろいろ拡張機能があって便利

最近、GithubでもQiitaでもMarkDownで書くことが増えて、HTMLのタグを書くのがめんどくさくなったので検索したらMarkDownをHTMLにかえてくれる便利なツールがあった。

# MarkDown PDFをインストール
VS Codeの横にある拡張機能ボタン(5つあるうちの一番下の四角いボタン)を押してMarketplaceでMarkDown PDFを検索してインストールします。
 ![markdown.PNG](https://qiita-image-store.s3.amazonaws.com/0/227535/9f5764f3-8707-03a5-b913-41d01fe897e4.png)

# コマンドパレットを開く
Windowsで`Ctrl+Shift+P`を叩くとメニューが表示されるので、MarkDown PDFのExport(html)やExport(pdf)などを選択して出力
![2018-07-22.png](https://qiita-image-store.s3.amazonaws.com/0/227535/743a309b-7c1e-2643-b02d-d34547323afa.png)

# HTMLが出力される
![2018-07-22 (1).png](https://qiita-image-store.s3.amazonaws.com/0/227535/5f43286c-68bd-89d8-4338-689d213985e9.png)

# まとめ
VSCodeは便利。デバッグもできる。AzureやDockerhubとの連携もできるらしい。おすすめ。
[sudoも使いたい]PhpStormでVagrant上のCLIのPHPをXdebugする

こちらの記事を参考にするとCLIのPHPをXdebugできる。
[PhpStormでVagrant上のCLIのPHPをXdebugする](https://qiita.com/tanakahisateru/items/4a186c3737215884d1a3)

しかし、以下のように`sudo`を使用している場合、環境変数が引き継がれないため、
Xdebugが動いてくれない。

```bash
export PHP_IDE_CONFIG="serverName=test.vagrant"
export XDEBUG_CONFIG=""
sudo -u user1 /bin/bash Console/cake ShellName1
```

そんな時は、`-E`オプションを付けると環境変数を引き継いでくれるので、
動いてくれる。

```bash
export PHP_IDE_CONFIG="serverName=test.vagrant"
export XDEBUG_CONFIG=""
sudo -u user1 -E /bin/bash Console/cake ShellName1
```

もしくはワンライナーで

```bash
PHP_IDE_CONFIG="serverName=test.vagrant" XDEBUG_CONFIG="" sudo -u user1 -E /bin/bash Console/cake ShellName1
```

環境変数を引き継ぐ方法は他にも方法はあるけど、取り急ぎはこれで対処できる。
快適なXdebugライフを！

参考：
[sudo 後の環境変数を設定する方法たち](http://nogiro.hatenablog.com/entry/2018/03/16/204843)
githubチュートリアルのメモ

#必要環境
タブブラウザとgithubのアカウント

#概要
githubの使い方を学ぶ。

- リポジトリの作り方
- ブランチ（枝）の派生と合流
- ファイル変更と登録（コミット）
- プルリクエストの開き方とマージ

# リポジトリの作り方
リポジトリはプロジェクトごとの入れ物。画像やテキストや動画、ソースコートなど、データセットの入ったフォルダなどが入れられる。
入れたデータの説明を書いたREADMEを入れておくとみんなそれを見る。

##　作り方
1. ブラウザでログインして、右上のアバターの隣の”＋”をクリックして、”new repository”をクリック
2. リポジトリの名前を記入
3. プロジェクトの概要を記入
4.  ”Initialize this repository with a README.”にチェック
5.   Create repository. をクリック

#　ブランチの派生と合流
ブランチはプロジェクトへ機能追加する際などに使う。ブランチを生成すると、ある時点でのメインのリポジトリ（master）のコピーが出来上がる。このコピーに機能追加やバグフィックスを実施後、masterへの合流(merge)をリクエストする。複数人で作業している場合、議論の末、masterへmergeできる。ブランチで作業中にmasterに変更があれば、変更を取り込むことができる。

## ブランチの生成
1. 作成したrepositoryに移動（https://github.com/ユーザ名/リポジトリ名）する。
2. 左上のbranch：ブランチ名のタブボタンをクリック
3. 生成するブランチ名を入れてenter
4. タブボタンを見ると2つのブランチ名ができている。現在見えている（選択した）ブランチにはチェックボックスが入る。


# ファイルの変更と登録
ここでは先ほど生成したブランチのREADMEの内容を変更し、これを登録(commit)する。
自分がmasterブランチ（幹）にいる（見ている）のか、先ほど生成したブランチ（枝）にいるのかに注意する。

## 方法
1. リスト内のREADME.md をクリックする。
2. 右上の鉛筆ボタンをクリック。
3. エディタで編集する。
4. 変更点等を記述したコミットメッセージを記入し、commit　changeボタンをクリック

# プルリクエストとマージ
ブランチ（枝）で変更登録した内容をmaster(幹)に反映させる依頼（プルリクエスト）をかける。
masterとの差分はわかりやすく表示され、ほかの人からコメントをもらうことができる。
問題がなければマージできる。

## プルリクエストの出し方
1. Pull requestタブに移動し”New Pull Request”ボタンを押す。
2. 変更したファイルのリストが表示され、これをクリックすると、マスターとの変更点が表示される。
3. 問題なければ"Create Pull Request"ボタンをクリックする。
4. Open Pull Requestの画面が出てくるので、タイトルとコメントを入力し、"Create Pull Request"ボタンをクリック。
5. Pull requestタブにリクエストの数が表示されていることがわかる。

## マージ
1. 緑のMerge pull requestボタンをクリック。
2. Confirm mergeボタンをクリック
3. Pull requestタブに表示されているリクエストの数が減っていることを確認。
4. masterのプロジェクトが変更されている。
5. Pull requestタブのclosedの数が増えている。

## 不要ブランチの削除
1. Pull requestタブのclosedをクリック
2. Delete Branchのボタンをクリック


#参考　
https://guides.github.com/activities/hello-world/
VisualStudioでDjangoアプリの作成と管理アプリの有効化を行う

# VisualStdioでDjangoの新しいアプリを作成し、管理者アプリを有効化する

## VisualStudioでDjangoWebAppを作成
`ファイル > 新規プロジェクト > 作成`

pythonタブからDjango Webアプリを作成

## Adminアプリを有効化する
url.pyの最後のほうにあるadminアプリのコメントアウトを削除して、

```url.py
    # Uncomment the admin/doc line below to enable admin documentation:
    url(r'^admin/doc/', include('django.contrib.admindocs.urls')),

    # Uncomment the next line to enable the admin:
    url(r'^admin/', include(admin.site.urls)),
```

import部分にadminを追加

```url.py
from django.contrib import admin
```

## 管理者アプリのユーザを作成する

地味にはまったのが、管理コンソールで`manage.py createuser`とかしても動かないこと。
(やり方知っている人がいたら教えてください...。)
基本的にmigrateとかもプロジェクト以下のボタンをポチポチしてできる。

`プロジェクト > Djangoでスーパーユーザーを作成する`　を選択

コンソールでユーザ名、メールアドレス、パスワードを設定

## 実行

Webサーバーを実行(緑の矢印ボタンを押すだけ)
`http://localhost:xxxx/admin/`にアクセスしてログインできたら完了
前処理の時によく使うPythonメソッド(随時更新)

自分用メモ
# データ読み込み
## フォルダ内にあるcsvファイルの一覧を取得

ファイル名のみ取得したい場合

```py
import os
path = "ディレクトリパス"
csv_files = [f for f in os.listdir(path) if f.endswith(".csv")]
csv_files
```

```py
[a.csv,
 b.csv,
 c.csv]
```

絶対パスを取得したい場合

```py
import glob
files = glob.glob("ディレクトリパス/*.csv")
```
[ディレクトリパス/a.csv,ディレクトリパス/b.csv,ディレクトリパス/c.csv]

## pd.read_csvでエラーが出た時の対処法
### FileNotFoundError
ディレクトリ変更されてない

```py
os.chdir("\データのあるディレクトリ")
```
でディレクトリを指定する。

### UnicodeDecodeError
文字コードが違う

```py
df_train = pd.read_csv("train.csv" , encoding="shift-jis")
```

Shift_JISx0213じゃないとダメなときもある

#探索的データ解析(EDA)
### データ概要を見るためのメソッド

```py
df.head()
df.tail()
df.info()
df.describe()
df.dtypes 
```
###列のタイプをカウントする

```py
df.dtypes.value_counts()
```
float64    65
int64      41
object     16
dtype: int64

###オブジェクトタイプ列の値の種類(カテゴリカル変数の特定)

```py
df.select_dtypes('object').apply(pd.Series.nunique,axis=0)
```

性別 3
国   199
言語 132

###データの抽出

```py
df = df[df["合計"]!=0]
```

### グループごとの平均をみる

```py
df.groupby("種別")["合計"].mean()
```

#前処理データ加工(Preprocessing)
### 列のドロップ

```py
df=df.drop("Unnamed: 0",axis=1)
```

### インデックスのセット

```py
df = df.set_index("合計")
```

###文字列を数値リテラルに変換

```py
df['Amount'] = pd.to_numeric(df['Amount']) 
```

### 値の置き換え

```py
df = df.replace('↓','0')
```

### datetime型変換

```py
df['time'] = pd.to_datetime(df['time'])
```

###特定列の値取得(重複なし)
```py
resion_list = list(set(df['地域名']))
```

###トレーニング、テストデータどちらにもある列のみ残す
```py
df_train,df_test = df_train.align(df_test,join='inner',axis = 1)
```

## 欠損値の処理
###欠損値の確認
```py
df.isnull().sum()
```

###null値に0を代入

```py
df = df.fillna(0)
```

### null値がある行を削除

```py
df.dropna()
```
JavaFX 下調べ

##ガイド
[リンク：JavaFXスタートガイド（Oracleサイト）](https://docs.oracle.com/javase/jp/8/javafx/get-started-tutorial/index.html)
基本的な考え方をここで学べる。

##サンプルアプリケーション
[リンク：サンプルアプリケーション（Oracleサイト）](http://www.oracle.com/technetwork/java/javase/overview/javafx-samples-2158687.html)
上記のリンクページの「Try Ensemble 」をクリックしてサンプルダウンロード後、実行すればよい。
このサンプルアプリケーションがかなり便利で、気になる要素名を検索ボックスに入れて検索すると、それに応じたサンプルアプリケーションにアクセスできる。
さらにすべてのサンプルアプリケーションのソースが見れるため、下手にググるより早く課題解決する可能性がある。
なんとこのソース、サンプルアプリケーション上で閲覧できる。

##Scene Builder (GUI作成エディタ）
[リンク：Scene Builder（Gluonサイト）]
(https://gluonhq.com/products/scene-builder/)
こちらから、GUI作成ツールがダウンロードできる。
Java8以降、OracleからGluonへ開発は移管されたとのこと。
2018/07/22現在、日本語版をダウンロードすると文字化けするため、以下の対応で英語化する必要がある。日本語化しなくても簡単な英語が多いので問題ない。

[リンク：日本語訳された方の記事](https://qiita.com/ktgw0316/items/0650374eae22610fd15d)
[リンク：文字化け対処方法の紹介記事]
(https://qiita.com/izayoi5776/items/6e06265c8761a1753f61)

## Java9以降のJavaFX
現在は、Gluonにて、メンテナンスされており、またMaven Repositoryに登録されたので、
gradleやmavenを利用したダウンロードがサポートされている。

[gradleを用いたダウンロード適用方法](https://openjfx.io/openjfx-docs/#gradle)
Pythonでリストをマージする

リストを結合してマージしたかったので検索結果をメモ

## 方法
リスト同士の結合後に集合(set)に入れることで重複を削除します。
順番は移動するので順番に意味がある場合は別の方法で実装する必要があります。

``` python3
# リストを定義
list1 = [2, 3, 5, 7, 11, 17, 19, 23]
list2 = [2, 3, 7, 43]

# リスト同士の結合
list1.extend(list2)
print(list1)

# 重複を除外する
set1=set(list1)
print(set1)
```
```
[2, 3, 5, 7, 11, 17, 19, 23, 2, 3, 7, 43]
{2, 3, 5, 7, 11, 43, 17, 19, 23}
```

## 参考URL
[Python Tips：リストから重複した要素を削除したい - Life with Python](https://www.lifewithpython.com/2013/11/python-remove-duplicates-from-lists.html)
[baserCMS]コンテンツ管理上でのアクセス制限のURLを確認したいとき


baserCMS4系のコンテンツ管理画面上で、「コンテンツの新規追加」をアクセス制限したいURLを確認したい場面がありましたので、ちょっとしたTips残しておきます。

## 想定している対象者
- baserCMSでウェブサイトを制作をしている方
- PHPer


## 発生状況
1. baserCMSの「コンテンツの新規追加」をクリックしたときに表示される選択内容を制限したい

### 環境
- baserCMS 4.1.2（4系全般）

## 対処
- /lib/Baser/View/Helper/BcContentsHelper.php

setup() 内の $setting['url']['add'] を覗いてみると良い。

```php
// disabled
var_dump($setting['url']['add']);
$setting['addDisabled'] = !($this->_Permission->check($setting['url']['add'], $user['user_group_id']));
```

上記の箇所で該当URLに対するアクセス権限をチェックしてました。
lower_bound、upper_boundの基本的な使い方

どちらも二分探索を行う関数で、関数呼び出し時に探索したい値を指定する。

## lower_bound
探索したい値**以上**が現れる最初の位置のイテレータを取得。
インデックスを取得したい場合は、`取得したイテレータ - 探索したい領域の先頭`すればよい。

例）
探索したい領域 : `vector<int> v = {1, 2, 3, 4, 5}`
探索したい値 : `3`
結果 : 探索したい値**以上**なので、`3`の位置のイテレータが取得される。

```c++
#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;

int main(){
	vector<int> v = {1, 2, 3, 4, 5};
	auto it = lower_bound(v.begin(), v.end(), 3);

	int index = it - v.begin();
	
	// output
	//   index: 2
	//   value: 3
	cout << "index: " << index << endl;
	cout << "value: " << v[index] << endl;
	return 0;
}
```

探索したい値が見つからなかった場合。`領域の最後のイテレータ`が返される（？）

```c++
	vector<int> v = {1, 2, 3, 4, 5};
	auto it = lower_bound(v.begin(), v.end(), 7);

	int index = it - v.begin();
	
	// output
	//   index: 5
	//   value: 0
	cout << "index: " << index << endl;
	cout << "value: " << v[index] << endl;
	return 0;
```


## upper_bound
探索したい値**より大きい値**が現れる最初の位置のイテレータを取得。

例）
探索したい領域 : `vector<int> v = {1, 2, 3, 4, 5}`
探索したい値 : `3`

```c++
#include<iostream>
#include<vector>
#include<algorithm>
using namespace std;

int main(){
	vector<int> v = {1, 2, 3, 4, 5};
	auto it = upper_bound(v.begin(), v.end(), 3);

	int index = it - v.begin();
	
	// output
	//   index: 3
	//   value: 4
	cout << "index: " << index << endl;
	cout << "value: " << v[index] << endl;
	return 0;
}
```

探索したい値**より大きい値**なので、`4`の位置のイテレータが取得される。
HTML,Webカメラで残像パンチを打ってみた

![パンチ.gif](https://qiita-image-store.s3.amazonaws.com/0/259333/33d482c1-f48a-d1a6-ec72-00c9725c6f78.gif)
#やり方
Webカメラをブラウザ上に表示
↓
CanvasにWebカメラの画像を書き出す
書き出す時の透明度を0.5に設定
↓
setInterval で繰り返し

```HTML
<body>
残像
<canvas id="canvas" width="400" height="300" style="border: solid 1px"></canvas>
元動画
<video id="camera" width="400" height="300" autoplay="1" class="camera" style="border: solid 1px"></video>


<script type="text/javascript">
navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia || window.navigator.mozGetUserMedia;
window.URL = window.URL || window.webkitURL;

var video = document.getElementById('camera');
var localStream = null;
navigator.getUserMedia({video: true, audio: false}, 
    function(stream) { // for success case
    console.log(stream);
    video.src = window.URL.createObjectURL(stream);
    localStream = stream;
    },
    function(err) { // for error case
    console.log(err);
    }
);

//canvasに描画権利を与える
var canvas = document.getElementById('canvas');
var ctx = canvas.getContext('2d');
var img = document.getElementById('img');

//videoの縦幅横幅を取得
var w = video.offsetWidth;
var h = video.offsetHeight;

//同じサイズをcanvasに指定
canvas.setAttribute("width", w);
canvas.setAttribute("height", h);

var record = function(){
    //canvasにvideoタグ画像をコピー
    ctx.globalAlpha = 0.5;
    ctx.drawImage(video, 0, 0, w, h);
}

setInterval(function(){
    record();
},100);
</script>
 </body>


```

> 参考URL
> カメラを使ってみよう ーWebRTC入門2016
https://html5experts.jp/mganeko/19728/
Reactコンポーネント化を複雑化させないための最低限の考え方

## はじめに
最近、React開発を始めたばかりのフロントエンドエンジニアです。
ReactでライフサイクルやState管理など、理解はできてきたものの、
コンポーネントが複雑化してきて、非常に困っていたため、
整理のために書きました。

なにかご指摘がありましたら、積極的にコメントをいただけるとありがたいです。


# とりあえず、考えることは一つ！

Reactのコンポーネントを役割で分ける、ということ！
具体的にいうと、コンポーネントを
　レンダリングを担当するもの
　データ構造や、データの流れを担当するもの
に分けます。

その二つについて、解説していきます

※内容的には、Reduxの公式(http://redux.js.org/docs/basics/UsageWithReact.html)
に乗っているものと同じ内容ですが、Reduxを使っていなくても、コンポーネントの整理には有効かと思います。

#レンダリングを担当するもの(Presentational Component)
Presentatinal Componentは、
どのように見えるかのみに焦点をあてたコンポーネントで、propsで与えられたデータで、レンダリング時にどう表現するかを記述します。
そのため状態を持つ必要がないので、Reactを継承しなくて軽いStateless Functional Componentで記述します。
(※propsで渡ってくる値を一般化すると汎用性が増す　
悪い例： 

``` ParentPage.jsx
import Task from '/template/Task'

export default class ParentPage extends React.Component {
...

<Task openTaskDetail={()=>this.openTaskDetail()} />
...
}
```
で渡し、

``` Task.jsx
const Task = (props) => {
 return (<h1 onClick={props.openTaskDetail} >Click!!</h1>)
}
```
で発火

いい例：

``` ParentPage.jsx
import Task from '/template/Task'

export default class ParentPage extends React.Component {
...

<Task handleClick={()=>this.openTaskDetail()} />
...
}
```
で渡し、

``` Task.jsx
const Task = (props) => {
 return (<h1 onClick={props.handleClick} >Click!!</h1>)
}
```
で発火

#データ構造や、データの流れを担当するもの(Container Component)
Presentetional Componentを内包し、
基本DOMの構成はせず、
Presentational Componentへのpropsの受け渡しを担当する。
データの生成もここで行う。
そのため、どのように見えるかについてはまったく関与しなくて良い
(※Container Componentでデータを渡すときは、何をレンダリングするコンポーネントに渡しているかが、わかりやすい下位コンポーネントを持つべき

悪い例：

``` Shop.jsx
<TitleText  name={shop.name} />
<FlexRow>
 <Circle badge={shop.cart} />
 <Circle badge={shop.customer} />
</FlexRow>
<Number number={shop.tel} />
<GrayText text={shop.information} />
```
良い(?)例：

``` Shop.jsx
import ShopStatus from '../template/ShopStatus'
import ShopInformation from '../template/ShopInformation'

<ShopStatus name={shop.name} badgeCart={shop.cart} badgeCustomer={shop.customer} />
<ShopInformation tel={shop.tel} information={shop.information} />

// こっちの方が、コンポーネントが値をなんのために渡しているのか、わかりやすい！
```

#まとめ
コンポーネントは
Presentatinal Componentは、レンダリング
Container Componentは、データ構造や、データの流れに対して責任を持つ
で分けよう。

それを理解した上で、Atomic　Designの考え方を取り入れると整理されて、とてもソースが見やすくなる、、、はず！！
[超初心者向け] まっさらなMacにRuby2.5.1をインストールする

ターミナルで以下コマンドを入力

```sh
# コマンドラインツールのインストール
xcode-select --install

# homebrewのインストール
ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"

# homebrewのからrubyのversion管理ツールをインストール
brew install rbenv ruby-build

# rbenv経由でruby 2.5.1をインストール
rbenv install 2.5.1

# rbenvの設定
echo 'eval "$(rbenv init -)"' >> ~/.bash_profile

# rbenvの設定を反映
source ~/.bash_profile

# rubyのversionを変更
rbenv global 2.5.1 
rbenv rehash	
```

参考
[MacでRuby on Rails環境構築 - Qiita](https://qiita.com/unsoluble_sugar/items/c2a26ff7f08e5b893896)
ml agent toolkit(0.4) windows7 やり方と変わった内容

うちのパソコン、試したパソコン：windows7

editorで学習できるようになる
もっと構造がシンプルになった学習速度も速くなり前のバージョンと大きく変化した
セーブデータをロードしたりする方法も少し変わった
人工知能に関するとか大体の内容は全然変わってない、バクトルスペースとかは変化あり https://github.com/Unity-Technologies/ml-agents/blob/master/docs/Migrating.md 、
人工知能の理論の内容とかはめちゃちょい言った。いいアイデアとは思う。https://blogs.unity3d.com/jp/2018/06/19/unity-ml-agents-toolkit-v0-4-and-udacity-deep-reinforcement-learning-nanodegree/ ここくらい、英語

名前も新しくtoolkitが付けられた
cd　でml agentフォルダに移動するpythonに移動する　pip install .！！！！！！！必ず点.つけよ！！！！！！！！
learn.pyが（windowsでは）unicodeエラーが出る
spyderでlearn.pyスクリプト

    
                    ▄▄▄▓▓▓▓
               ╓▓▓▓▓▓▓█▓▓▓▓▓
          ,▄▄▄m▀▀▀'  ,▓▓▓▀▓▓▄                           ▓▓▓  ▓▓▌
        ▄▓▓▓▀'      ▄▓▓▀  ▓▓▓      ▄▄     ▄▄ ,▄▄ ▄▄▄▄   ,▄▄ ▄▓▓▌▄ ▄▄▄    ,▄▄
      ▄▓▓▓▀        ▄▓▓▀   ▐▓▓▌     ▓▓▌   ▐▓▓ ▐▓▓▓▀▀▀▓▓▌ ▓▓▓ ▀▓▓▌▀ ^▓▓▌  ╒▓▓▌
    ▄▓▓▓▓▓▄▄▄▄▄▄▄▄▓▓▓      ▓▀      ▓▓▌   ▐▓▓ ▐▓▓    ▓▓▓ ▓▓▓  ▓▓▌   ▐▓▓▄ ▓▓▌
    ▀▓▓▓▓▀▀▀▀▀▀▀▀▀▀▓▓▄     ▓▓      ▓▓▌   ▐▓▓ ▐▓▓    ▓▓▓ ▓▓▓  ▓▓▌    ▐▓▓▐▓▓
      ^█▓▓▓        ▀▓▓▄   ▐▓▓▌     ▓▓▓▓▄▓▓▓▓ ▐▓▓    ▓▓▓ ▓▓▓  ▓▓▓▄    ▓▓▓▓`
        '▀▓▓▓▄      ^▓▓▓  ▓▓▓       └▀▀▀▀ ▀▀ ^▀▀    `▀▀ `▀▀   '▀▀    ▐▓▓▌
           ▀▀▀▀▓▄▄▄   ▓▓▓▓▓▓,                                      ▓▓▓▓▀
               `▀█▓▓▓▓▓▓▓▓▓▌
                    ¬`▀▀▀█▓
                    
形同じ奴をこれで変える（だめなら完全にそのラインを消します（それも全然あり））

python learn.py --run-id='oppai1' --train
して待ってるとStart training by pressing the Play button in the Unity Editorと言うので
EditorでBrainタイプをExternal Brain(s)にして再生ボタンクリック（完）
Proxy環境配下で使っている端末でJupyternotebookをProxy環境外で使った時にCannot connect to proxyが出てしまう問題を解決

#結論　どこの環境変数なのか注意
ハマりました。。
普段はProxy環境で使っている端末で、いざ違う環境で使うとプロキシを見てしまうということ
よくあると思います。
今回もOSの環境変数をなんとかすれば、動くだろうと思っていましたが、消してもなぜかプロキシを見に行ってしまう。
Cannot connect to proxy でタイムアウトエラーが治りませんでした:persevere:

# 一個ずつ確認すると
まずはOSの環境変数ですが、もともとbash_profileにhttp_proxy,https_proxyという名前で環境変数を私は設定していました。今回はそれを消せばOKかと思っていました。
しかし、、治りません。

# 色々試してみると
①ipynbファイルで実装している内容をpyファイルにして実行
　普通に実行結果が出力されました。
　それでもjupyter からはNGとなります。

②ipynbファイルで実装している内容をIPythonで実行
　普通に実行結果が出力されました。
　それでもjupyter からはNGとなります。

③.condarcは使っていないので、とりあえず、jupyterの中に限定して
環境変数か何かなと思いつつも起動ブラウザを変更して実行
私はsafariをデフォルトで使っていたため、

```
jupyter notebook --browser='chrome'
```
chromeでjupyterを起動しました。やっぱり、それでも結果が変わりません。

# jupyter上から環境変数を確認
ビルトインモジュールで環境変数を確認してみます。bash_profile上で削除されているため、
http_proxyとhttps_proxyは削除されているのが、以下、コマンドでわかります。

```python

import os
for k, v in os.environ.items():
    print("{key} : {value}".format(key=k, value=v))
```

jupyterのマジックコマンドで以下を確認すると、http_proxyとhttps_proxyが存在しています。

```python

%env
```

これが削除できれば大丈夫そうだと思い、以下のようにして削除というか設定値を空にしました。

```python

%env http_proxy =
%env https_proxy =
```

この設定により、無事、proxyを経由せずに正常にレスポンスが返ってきました。


# 最後に
意外とこの問題が記事になってなく、自分もまたこの状況になって忘れていたら嫌なので、
記事に残しました。
Server Side Swift -Kitura & Vapor-

# この記事について
この記事は[Swift Tweets](https://swift-tweets.github.io/) ([Swift Tweets 2018 Summer connpass](https://swift-tweets.connpass.com/event/84462/)) で発表したLTのまとめです。

後日swtws中に頂いた議論を元に追記予定です。

## Kitura vs Vapor ?
"Server Side Swift -Kitura & Vapor-"というタイトルで発表をしました。@el_hrhmです。よろしくお願いします。
Kitura と Vapor を使って簡単なWebアプリを使ってみて感じたことについて投稿します。
### 作ったもの
- APIサーバー
- 静的HTMLを返すWebページ用のサーバー
- Reactを使ったシングルページのサーバー
それぞれをKitura, Vaporを使って作成し、比較してみました。

### 使い心地
結論としては、両者にスタイルの違いはあるものの、使い心地はどちらも良いと感じました。


両者はコーディングスタイルの違いもそうですが、Swiftの新しい機能の取り入れ方に差があります。
VaporはFutureを使って記述できるようにするなど、より使いやすくなるよう進化を速めている印象です。
一方Kituraはより進化の影響を外部に流出させないよう注意深く作られていて、固い印象を持ちました。
しかし、どちらも十分にドキュメントが充実しており、読めばやりたいことは大体できました。
(ドキュメントが膨大で、必要な情報を探し出すのに苦労するかもしれません。)
また、どちらのフレームワークも質問のための窓口があるので、困ったら投げてみると良いと思います。
(KituraはSlack, VaporはDiscord)

実際のプロダクトに適用するには、Kituraの方がプロダクトコードを変えずにバージョンを上げやすそうです。
しかし、より記述しやすい機能を提供するという点においてはVaporに軍配が上がると思っています。
どちらもまだまだ発展途上でこれから変わっていくので、どちらを採用するかは開発やプロダクトのスタイルが決め手になるでしょう。

### How to Web Server
まず、クライアントからのリクエストに対してルーティングを記述します。どちらのフレームワークも簡単に記述できます。
APIサーバーであれば例えばJSON形式のレスポンス、Webページの表示ならHTMLや画像、jsファイルなどをクライアントに返します。
HTMLを返すサーバーであれば、コンポーネントを要求に応じて構築し、返す形にすれば良いでしょう。構造化された文書をSwiftで表現するのは可読性が高く、型による安全性も得られるので素晴らしいと感じました。

```swift

let html = """
<!DOCTYPE html>
  <html>
    \(htmlheader.html)
    \(htmlbody.html)
  </html>
"""
```

Webページではブラウザから要求されるリソースを返すようにサーバー側で定義する必要があります。こちらはKituraでのコードです。
適切なHTTPヘッダーを返す必要があるので、拡張子によって切り替えています。

```swift

app.router.get("/:filename") { request, response, next in
    if let filename = String?(request.parameters["filename"]!){
        response.headers.append("Content-Type", value: responseContentType(path: filename))
        try response.send(fileName: "./dist/\(filename)")
    } else {
        response.statusCode = HTTPStatusCode(rawValue: 500)!
        response.send("500 internal server error")
    }
    next()
}
```

シングルページであれば、webpackでbundle.jsを作るなどして、それをサーバーで返すようにすればできます。例えば以下のようにして、index.htmlでbundle.jsを要求するようにします。

```swift

app.router.get("/") { request, response, next in
    response.headers.append("Content-Type", value: "text/html; charset=utf-8")
    let filePath = "./dist/index.html"
    
    do{
        let str :String = try String(contentsOf: URL(fileURLWithPath: filePath))
        response.send(str)
    } catch {
        response.statusCode = HTTPStatusCode(rawValue: 500)!
        response.send("500 internal server error")
    }
    next()
}
```

## まとめ
- KituraもVaporもいい感じ。好きな方でSSSしよう！
- 現状はAPIサーバーが良さそうです！