OmniAICreator/Qiita-1.07M huggingface dataset:
jQueryの基礎構文についての備忘録

jQueryを使う恩恵は３点だと思っています。

①クロスブラウザな実装ができる点
②短い記述でDOM操作ができる点
③簡単にAJAXが実装できる点
　

そんなjQueryを使う前にまずこれだけは覚えておきましょうという基礎。

まずはjQueryの使い方から。

```js
$(function(){
    $('#btn1').on('click', function(){
        $('#txt').css('color', 'red');
    });
});

```  

　
```$(function(){~~~});```
部分は
```$(document).ready(function(){~~~});```

のシンタックスシュガーになります。
```(document).ready```はHTML上の全DOM要素の読み込み後に走ります。


そのfunction内にそれぞれのイベントハンドリングを書き足していきます。

ここからは、記事最下のURLがよくまとまっていたので引用しています。


#①.click()ではなく.on()#

```js
$('#btn').on('click', function() {
    alert('hogegenoge');
})

```
.click()とか使うのは辞めましょう。

.on()では
.click(), bind(), live(), delegate()を包括しています。

.clickの場合は、
ページのレンダリング時点で存在しておらず
後からfunctionなどを使って追加したDOM要素に対しては
イベントの設定ができません。

#②success:, error:ではなく.done(), fail()##
以下にまとめました。
[jQueryのdeferred用いたajaxについての備忘録](https://qiita.com/mounntainn/items/37407e1ced0ce8c23101)

#③POSTだけなら.ajax()ではなく.post()
postの方がシンプルにかけます。


#④子要素の検索なら.find()#
```$('.hoge #hogege')```
よりも
```$('.hoge').find('#hogege')```
がベターです。

ちなみに.はクラスで検索、#はIDで検索ですね。




まだjQuery覚え始めたところですが
もうすでにjQueryよりもこれからはReact.jsのようですがね。

モダンな開発が進む時代に取り残されないようにまだまだ勉強必要です……

---
参考:
[jQuery使いが知っておくべきjQueryテクニック8選](http://blog.toshimaru.net/jquery-8-tips/)
MATLAB > unique(vs, 'rows')を使ってみた > [res, ~, idx] = unique(vs, 'rows')

```txt:動作環境
GeForce GTX 1070 (8GB)
ASRock Z170M Pro4S [Intel Z170chipset]
Ubuntu 16.04 LTS desktop amd64
TensorFlow v1.2.1
cuDNN v5.1 for Linux
CUDA v8.0
Python 3.5.2
IPython 6.0.0 -- An enhanced Interactive Python.
gcc (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
GNU bash, version 4.3.48(1)-release (x86_64-pc-linux-gnu)
scipy v0.19.1
geopandas v0.3.0
MATLAB R2017b (Home Edition)
```

### 関連

[MATLAB > [v,~,idx] = unique(v,'rows'); > tilde(~):プレースホルダ > Pythonでの下線(_)に相当するのだろう](https://qiita.com/7of9/items/8116a12880f41314e279)

### 使ってみた。

MATLAB Onlineで確認。

https://jp.mathworks.com/help/matlab/ref/unique.html

```matlab
>> vs = [ 3 1 4; 1 5 9; 1 5 9; 2 6 5; ];
>> [res, ~, idx] = unique(vs, 'rows')

res =

     1     5     9
     2     6     5
     3     1     4


idx =

     3
     1
     1
     2
```

idxの「3, 1, 1, 2」の意味は以下のようなものだろう。

- 3: vsの1行目はresの3行目 (3 1 4)に対応する
- 1: vsの2行目はresの1行目
- 1: vsの3行目はresの1行目
- 2: vsの4行目はresの2行目
[Ruby]オーバーライドしたメソッドをスーパークラスのメソッドから呼んだ時の動き

# ソース
```rb
class TestClass
  def method1
    p("this is TestClass#method1")
  end

  def run
    method1
  end
end

class TestClass2 < TestClass
  def method1
    p("this is TestClass2#method1")
  end
end

TestClass2.new.run
```
# 実行結果
```
"this is TestClass2#method1"
```
サブクラスのメソッドが呼ばれる。
オフラインリアルタイムどう書く F08 を Rubyで解いた

問題：http://nabetani.sakura.ne.jp/hena/ordf07chairs/
実装リンク集：https://qiita.com/Nabetani/items/de5b9d3230603033ed74

問題の理解に時間がかかりました。最終的に出題者に確認する嵌めに・・・。

```ruby
def availables(status)
  seats = status.keys
  seats.each.with_object(0 => [], 1 => [], 2 => []) do |n, o|
    next unless status[n] == '-'
    i = seats.index { |s| s == n }
    left, right = [-1, 1].map { |a| status[seats[(i + a) % seats.size]] == '-' ? 0 : 1 }
    o[left + right].push(n)
  end
end

def push(status, c)
  a = availables(status)
  (0..2).each do |n|
    next unless a[n].size.positive?
    a[n].sort!
    seat = c <= 'M' ? a[n].first : a[n].last
    status[seat] = c
    break
  end
end

def calc(src)
  status = '135798642'.chars.each.with_object({}) { |n, o| o[n] = '-' }
  src.chars.each do |c|
    if c.upcase == c
      push(status, c)
    else
      seat = status.select { |_k, v| v == c.upcase }
      status[seat.keys[0]] = '-' unless seat.empty?
    end
  end
  status.map { |_k, v| v.to_s }.join
end

DATA.each do |d|
  n, src, exp = d.split
  act = calc(src)
  puts %(#{n} #{act} != #{exp} (#{src})) unless act == exp
end

__END__
0 	NABETanI 	I-E--T-B-
1 	A 	A--------
2 	Aa 	---------
3 	Z 	----Z----
4 	Zz 	---------
5 	AaB 	B--------
6 	ABa 	-------B-
```
reactでmapする要素を切り出したときにkeyを指定する

reactのコンポーネント内でmapなどの繰り返し処理を使ってリストを作成する場合、keyを指定しなければならない。

## keyを指定しないともちろんエラーが起きる
```js
render(){
  const {list} = this.state;
  return(
    <ul>
      {list.map((item, i) => {
        return <li>hogehoge</li>
      })}
    </ul>
  )
}
```

reactが吐いてくれるエラー
`unique keyを指定してよ！`っていうよくあるやつですね

```
warning.js:34 Warning: Each child in an array or iterator should have a unique "key" prop. See https://fb.me/react-warning-keys for more information.
```

## keyを指定するとエラーが起きない
もちろんkeyを指定するとエラーが起きません。

```js
render(){
  const {list} = this.state;
  return(
    <ul>
      {list.map((item, i) => {
        return <li key={i}>hogehoge</li> //keyを指定
      })}
    </ul>
  )
}
```

## mapする要素を外に切り出したときのkey
例えば、mapする要素が大きくなって外に切り出したくなったとする
この場合、keyを付けないともちろん先ほどの`unique keyつけてよ！`っていうエラーが起きる。

この場合、keyは子コンポーネントの中の要素には付けなくてよく、コンポーネントにkeyを渡すだけでよい。

```js
render(){
  const {list} = this.state;
  return(
    <ul>
      {list.map((item, i) => {
        return <List item={item} key={i} /> //keyを渡す
      })}
    </ul>
  )
}
...
const List = ({item}) => {
  return(
    <li>{hoge}</li> // 子コンポーネントには必要なし！
  )
}
```

地味にハマったのでメモっておきました。
Oracle SQL Developer Tips. ファイル選択ダイアログのナビゲーションペインにフォルダを追加したい


## はじめに

Windows 版を例に挙げます。その他のプラットフォームでは若干異なるかもしれません。

## 用語について

「ナビゲーションペイン」というのかどうか不明ですが、Windows のファイルブラウザである「エクスプローラー」のナビゲーションウィンドウに当たるイメージです。

## 背景

Oracle に付属する開発ツールのひとつ SQL Developer にて、SQL ファイルを開いたり、ログを採ったりとファイル選択（保存）ダイアログを使う機会は、少しあります。

特にログを採取しているときなど、同じフォルダに連続してアクセスする機会があります。

しかしながら、ファイル選択ダイアログの基点ディレクトリは都度リセットされてしまうので深い階層に毎回フォルダにアクセスしたい場合は不便です。

SQL Developer のファイル選択（保存）ダイアログには、左側のペインに Windows エクスプローラーでいうところの「ナビゲーションウィンドウ」に当たるようなペイン（枠）がありますが「ホーム」しか表示されていません。ここにフォルダ（ショートカット）を登録できれば上記のような場合に便利です。

## やりかた

どうも「お気に入り登録」など、ずばり直接的な機能はないようです。

しかし SQL ファイル（拡張子が .sql のテキストファイル）を開くと、その親フォルダがこのペインに表示されます。

この効果を利用して、頻繁にアクセスする場所に dmy.sql のようなテキストファイルを置き、それを SQL Developer で開いた状態にしておくとこのナビゲーションペインを「仮想お気に入り」のように使うことができ、作業中は便利です。

## 何時消えるのか謎

この「仮想お気に入り」は SQL Developer を終了させたときに下記のファイルに書き込まれるようです。

C:\Users\<yourName>\AppData\Roaming\SQL Developer\system<version>\o.sqldeveloper<version>\ide.properties

しかしファイルを開いたままでも時々この「ナビゲーションペイン」から消えます。
随時ファイルを開いて、この「仮想お気に入り」機能を維持します。

## 検索キーワード

Oracle SQL Developer ファイル選択 ファイル保存 ダイアログ
ナビゲーション お気に入り フォルダ ディレクトリ 登録
C++ Builder XE4, 10.2 Tokyo > NULLに対して.IsEmpty()を使うのは良くない | Indy: IdUDPClient1->ReceiveString()の戻り値がNULLの場合がある

```txt:動作環境
C++ Builder XE4
RAD Studio 10.2 Tokyo Update 2 (追記: 2018/01/05)
```

### 関連

- [C++ Builder > Error: Access violation at address XXXX in module 'プログラム名.exe' 読み取り of address XXXXXXXX. の原因特定 > 複雑なものは簡素化する](https://qiita.com/7of9/items/f83de363fe8d46795720)

### Error

> Access violation at address XXXX in module 'プログラム名.exe' 読み取り of address XXXXXXXX. 

上記のエラー原因を特定して、コードを見ると以下の状況だと分かった。
(コードは簡素化している)

```cpp
	String wrk = NULL;

	if (wrk == NULL) {
		ShowMessage(L"NULL1");
	}
	if (wrk.IsEmpty()) {
		ShowMessage(L"NULL2");
	} else {
		ShowMessage(L"something");
	}
```

上記の結果は以下となる。

- NULL1が表示される
- somethingが表示される

実コードにおいて、wrkはUDPからの受信を受ける。
特定条件においてwrkにNULLが入り、.IsEmpty()でない時の処理を実行して、`Access violation`が発生しているようだ。

### code > Indy使用

```Unit1.cpp
//---------------------------------------------------------------------------

#include <vcl.h>
#pragma hdrstop

#include "Unit1.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
	: TForm(Owner)
{
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button1Click(TObject *Sender)
{
	_di_IIdTextEncoding m_enqSJIS = IndyTextEncoding(932);

	String cmd = L"zabuuun!";

	IdUDPClient1->Host = L"192.168.0.79";
	IdUDPClient1->Send(cmd, m_enqSJIS);
	String res = IdUDPClient1->ReceiveString(1000, m_enqSJIS); // msec

	// ここでresはNULLになる
}
//---------------------------------------------------------------------------
```

上記の処理で相手先がいない場合、resは`NULL`が入ることを確認した。
resに対して.IsEmpty()を使うのは良くないだろう。

関連: [C++ Builder > 無効なポインタ操作 > 不定値でのFree()によるメモリ破壊 > その後の処理で「無効なポインタ操作」 | Free()でなくdeleteを使う | ヌルポインタ経由でのメンバ関数呼び出しはC++の仕様上は未定義の挙動](https://qiita.com/7of9/items/4d47d3f8013c67d630fa)

### コード変更

.IsEmpty()を使う処理の前にNULLチェックを入れることで,
「Access violation at address」エラーは出なくなった。
WSDLファイルからjarを生成する方法と注意点

```bash
# -clientjarオプションを使うためにはJDK7以上が必要
$ wsimport -clientjar hoge.jar <WSDL_URL>
```

## 注意点
サーバ側（Linux：RHEL7）にあるWSDLファイルをもとにjarを生成しようと、クライアント側（Windows：Windows7）で上記コマンドを実行したところ、中身が壊れたjarが生成された。サーバ側で再度上記コマンドを実行すると正しいjarが生成された。理由はよくわからないが、WSDLからjarを生成する際はサーバ側で生成し、それをクライアント側に渡す方が確実そう。
C++ Builder > Error: Access violation at address XXXX in module 'プログラム名.exe' 読み取り of address XXXXXXXX. の原因特定 > 複雑なものは簡素化する

```txt:動作環境
C++ Builder XE4
```

### Error

> Access violation at address XXXX in module 'プログラム名.exe' 読み取り of address XXXXXXXX.

上記はメモリ関連のエラーによる原因特定が難しい例である。

### 原因特定 2017-11-24

今日の原因特定の方法は以下とした。

1. watchdogを止める
    - 特有ハードウェアのwatchdogを使っているソフト
    - エラーと同時にwatchdogによりPC再起動がかかるのはデバッグが難しい
2. 動作内容の把握
    - 同時に動くフォーム、TThreadの把握
3. 同時に動くものを止めていく
    - 設定変更で止める
    - プログラム変更で止める

ある装置との通信プログラム(UDP)で上記のエラーが出ているようだと特定できた。
（ファイル保存処理と思っていたが、そちらは「結果」であって「原因」ではなさそうだ）。

### 複雑なもののデバッグ

複雑なものを複雑なままデバッグしようとする例は見かける。
そうなると「Engineering」ではなく「推測ゲーム」になる。

Engineerとしての正しい対処として、「複雑なものを簡素化する」ことをよく行い、それはうまくいっているように思う。

GitなどのVCSを使うことで、簡素化した後に元の状態に簡単に戻せるようになったこともデバッグ時間短縮に貢献している。
AlamofireでPOSTする

#学んだ事
Alamofireを使ってAPI通信

##ソースコード
```signupViewController.swift
func HttpRequest() {
        let url = "URLをいれてね"
        let headers: HTTPHeaders = [ 
            "Contenttype": "application/json"
        ]
        let parameters:[String: Any] = [
            "username": username,
            "password": password
        ]

        Alamofire.request(url, method: .post, parameters: parameters, encoding: JSONEncoding.default, headers: headers).responseJSON { response in
            if let result = response.result.value as? [String: Any] {
                print(result)
            }
        }

    }
```
自分はこれを使いたいタイミングで関数を呼び出して使ってます
POSTしたい内容をparametersに書いて投げてるんだと思います
http通信についての知識が皆無なためいい本とかあれば教えて欲しいです
アジャイルプラクティスを読んで

10年くらい前に出たアジャイルプラクティスを読んだのでまとめます。


### アジャイルマニフェスト
- プロセスやツールより、人と人との交流を
- 包括的なドキュメントより、動作するソフトウェアを
- 契約上の交渉よりも、顧客との協調を
- 計画に従うことよりも、変化に適応することを

### 小さな問題は小さなうちに解決　
- ログ、アラートの必要性

### 過ちに気づいたら、すぐに素直に認める
- 認めやすい環境
 1. 普段からそういう人間関係構築が必要
 2. MTGやwiki（コンフル）等、気軽に良かった事、悪かった事を共有出来る場の用意

### アジャイルツールキット
- wiki
- バージョン管理
- ユニットテスト
- ビルドの自動化

どんな時でも最初に最大の難問から取り組む

### 非難をしてもバグは直らない。
- 誰かの後ろ指をさすのではなく自分のできる解決策に注力する。
- バグを憎んで人を憎まず

### 応急処置の誘惑に打ち勝つ。
- いつでも綺麗なコードを見せられるように全力を尽くす。

### あらゆる分野のエキスパートになる必要はないが。。。
- 業界がどこへ向かっているかは把握する
- キャリアとプロジェクトの計画を立てる。

### 言われたことを額面通りに受け取ってはいけない。
- 問題の根本を理解するまでしつもんし続ける必要がある。

### 設計は、正しい方向を示す道しるべではあるが、土地そのものではない。
- 具体的な道順を事細かに指定するべきはない。設計に囚われてはいけない。

### コードの統合はリスクの温床
- このリスクを緩和するには早い段階から統合に取り掛かり定常的に統合を繰り返し続ける。

### 読む人に意図がきちんと伝わるコードを書く。
- 人に読めないコードが利口なコードであるはずない。
Ubuntu Linux 16.04 LTS Desktopのネットワーク設定ファイルの場所

Ubuntu Linux 16.04 LTS DesktopでGUIを用いて

- 設定アイコン
 - ネットワーク
 - 有線
 - オプション
 - 方式
 - アドレス
 - ネットマスク
 - ゲートウェイ
 - DNS
 
を設定し「保存」した時に設定ファイルがどこにあるのか。

```
/etc/NetworkManager/system-connections/有線接続 1
```
漢字が入る上にファイル名に半角スペースが入るという罠
zabbix3.4でzabbix_senderを送ろうとしたが(よくわからず)登録できなかった。

## zabbix_senderインストール

* https://www.zabbix.com/download
* http://repo.zabbix.com/zabbix/3.4/ubuntu/pool/main/z/zabbix/?C=M;O=D

```sh:69kbほどと小さい。(ubuntu16.04以降用)
wget "http://repo.zabbix.com/zabbix/3.4/ubuntu/pool/main/z/zabbix/zabbix-sender_3.4.4-3+xenial_amd64.deb"
dpkg -i zabbix-sender_3.4.4-3+xenial_amd64.deb
```

## zabbix server起動

* [Zabbix3.4をdockerで運用してVulsと連携させる　〜 その1 〜 Zabbixのインストール - Qiita](https://qiita.com/sikkim/items/5533dd55f28f2cc41cdd#zabbix%E3%81%AE%E8%B5%B7%E5%8B%95%E3%81%A8%E5%81%9C%E6%AD%A2)そのまま利用させていただきました。

```yaml:docker-compose.yml
version: '2'
services:

  mysql:
    image: mysql:5.7
    restart: always
    command: mysqld --character-set-server=utf8 --collation-server=utf8_unicode_ci
    volumes:
      - ./data/mysql:/var/lib/mysql
    expose:
      - "3306"
    environment:
      MYSQL_ROOT_PASSWORD: docker
      MYSQL_DATABASE: zabbix
      MYSQL_USER: zabbix
      MYSQL_PASSWORD: zabbix

  zabbix-server:
    image: zabbix/zabbix-server-mysql:alpine-3.4-latest
    restart: always
    volumes:
      - ./data/zabbix:/var/lib/zabbix
    environment:
      DB_SERVER_HOST: mysql
      MYSQL_USER: zabbix
      MYSQL_PASSWORD: zabbix
    ports:
      - "10051:10051"
    depends_on:
      - mysql

  zabbix-web:
    image: zabbix/zabbix-web-nginx-mysql:alpine-3.4-latest
    restart: always
    volumes:
      - ./data/fonts:/usr/share/zabbix/fonts
    environment:
      DB_SERVER_HOST: mysql
      MYSQL_USER: zabbix
      MYSQL_PASSWORD: zabbix
      ZBX_SERVER_HOST: zabbix-server
      PHP_TZ: Asia/Tokyo
    ports:
      - "80:80"
    depends_on:
      - mysql
      - zabbix-server
```

* http://localhost admin : zabbix でログイン。

## zabbix server側でキーの待ち受け

1 ホストの作成

![スクリーンショット_2017-11-24_15-26-29.png](https://qiita-image-store.s3.amazonaws.com/0/25728/b7c871e5-3764-31c0-9730-3b8c689be256.png)

2 ホスト名を`zabbix_sender`と入力(あとで指定するため忘れないよう)、追加を押下。

![スクリーンショット_2017-11-24_15-28-49.png](https://qiita-image-store.s3.amazonaws.com/0/25728/962a5e02-77b2-845c-ab3d-1cb1cf96e3b7.png)

3 zabbix_sender というホスト名が追加されたことを確認。`ディスカバリ`リンクをクリック。

![スクリーンショット_2017-11-24_15-31-12.png](https://qiita-image-store.s3.amazonaws.com/0/25728/ec747e39-a3a5-403d-096c-37cf18bc61fa.png)

4 ディスカバリルールの作成を押下

![スクリーンショット_2017-11-24_15-32-23.png](https://qiita-image-store.s3.amazonaws.com/0/25728/d0f0fb93-702b-4097-a43b-0ab485a229cf.png)

5 キーに `zabbix_sender` と入力。

![スクリーンショット_2017-11-24_15-34-52.png](https://qiita-image-store.s3.amazonaws.com/0/25728/540abee3-5de2-82f4-f706-35f4db31e6c5.png)


## zabbix serverに送信

```sh:送信
cut -f 1 -d ' ' /proc/loadavg \
 | zabbix_sender -z 64.222.222.222 -p 10051 -s "zabbix_sender" -k "sender_load1" -vv -o -
```

> zabbix_sender [4578]: DEBUG: answer [{"response":"success","info":"processed: 0; failed: 1; total: 1; seconds spent: 0.000169"}]
info from server: "processed: 0; failed: 1; total: 1; seconds spent: 0.000169"
sent: 1; skipped: 0; total: 1

うーむ、登録されない
新米のvimtutor勉強メモ

- normal modeでのcursor移動
    - `k`　上、 `3k` 三行上に移動
    - `j`　下、 `3j` 三行下に移動
    - `h`　左
    - `l`　右
    - `w`　次の単語に移動
    - `b`　前の単語に移動、`w`の逆
    - `0`　行頭に移動
    - `$`　行尾に移動

- insert modeとnormal modeの切り替え
    - insert->normal : キー`esc`
    - normal->insert : キー`i`
    - normal->insert : キー`a`
    - normal->insert : キー`A`　（行末にcursorが移動）
    - normal->insert : キー`o`:cursorの下の行に新行を追加
 
- 保存なしで、vim閉じる：normal modeで `:q!`

- 文字削除コマンド
    - `d``数値``モーション`
   
  - 文字削除例
      - 文字(削除後、normal modeまま)：normal modeでキー`x`
      - 文字(削除後、insert modeまま)：normal modeでキー`s`
      - カーソル位置から空白を含む単語の末尾まで(削除後、normal modeまま)：normal modeでキー`dw` (delete word)
      - カーソル位置から空白を含まない単語の末尾まで(削除後、normal modeまま)：normal modeでキー`de` (delete word)
      - 単語(削除後、insert modeまま)：normal modeでキー`cw` (change word)
      - カーソル位置から行末まで。(削除後、normal modeまま)：normal modeでキー`d$`
      - 行の削除： normal modeでキー`dd`,`3dd`(3行削除)

- モーション
    - w - カーソル位置から空白を含む単語の末尾まで。
    - e - カーソル位置から空白を含まない単語の末尾まで。
    - $ - カーソル位置から末尾まで
    - 0 - 行頭からカーソル位置まで 

- undo && redo
    - `u` - undo
    - `CTRL-R` - redo

- copy
    - visual modeで選択して、`y`を入力
  
- paste
    - `p` バッファをカーソルの後に挿入します(行単位で削除されたのならば、カー
     ソルのある次の行に挿入されます)

- 文字単位の置き換え
    - normal modeでキー`r`後、正しい文字を入力、置き換え処理後もnormal modeままである

- 変更コマンド
    - `c`    `[数値]`   `モーション`
    - `cw` - 単語を変更
    - `c$` - カーソル位置から末尾までを変更
    
- buffer（開いたファイル）の操作
    - bufferリストを出す: `:buffers`か`ls`
    - buffer内のファイルを開く: `:b2`　（２はbufferの番号、上記のリストからわかる）
    - buffer内のファイルを開く: `:b`+一部のファイル名+`tab`
    - bufferのファイルを閉じる: `:bd2`（２はbufferの番号、上記のリストからわかる）
    - bufferの現在編集中のファイルを閉じる: `:bd`

- ファイルを開く：　`:e`+ファイル名
- normal modeで一行の選択：　`V`

- 特定の行に飛ぶ
    - `G`:最下行
    - `gg`:先頭の行
    - `44G`:44行目
    - `ctrl+g`:ファイル情報と現在位置を表示

- 検索
    - `/検索内容`+<ENTER>:大小文字区別
    - `/\c検索内容`+<ENTER>:大小文字区別なし
    - `n`:次のmarchした位置に移動
    - `N`:前のmarchした位置に移動
    - `:set ic`: 大小文字区別なし(ignore case)
    - `:set noic`: 大小文字区別
    - `:set hls is`: 検索結果をhighlight
    - `:set nohlsearch`:検索結果highlightをやめる
 
- pairになる括弧に飛ぶ
    -  (,[,],{,},)のどれかにcursor移動してから、`%`を押す

- replace
    - `:s/thee/the`+<ENTER>:現在行の最初に見つかったものに対して
    - `:s/thee/the/g`+<ENTER>:現在行の全ての箇所
    - `:1,20s/thee/the/gc`+<ENTER>:1~20行の全ての箇所
    - `:%s/thee/the/g`+<ENTER>:ファイルの全ての箇所
    - `:%s/thee/the/gc`+<ENTER>:ファイルの全ての箇所＋一つ一つ確認が必要

- 外部コマンド実行
    - `:!コマンド`

- 保存
    - `w`:元のファイルに保存
    - `w　ファイル名`:ファイル名指定で保存
    - visual modeで選択した後、`:`+`w ファイル名`+<ENTER>:選択した部分のみを保存

- 他のファイル（コマンド結果）を現在の位置に挿入
    - `r ファイル名`
    - `r !コマンド`

- 置換モード(置換モードに入ると、すべてのタイプされた文字は既存の文字
      を削除します)
    - `R`

- 別のウィンドウへジャンプ: `CTRL-W CTRL-W`
- : command で可能な補完を見るには: `CTRL-D`
- 補完を使用するには: `<TAB>`

- 1行から5行まで削除：`:1,5d`
Docker構築備忘録

# 環境
windows10
Docker 17.09.0
docker-compose 1.16.1

# やりたいこと
dockerでWEBサーバとDBサーバとメールサーバを構築する
開発環境として利用するのでデータは永続化したい

``` docker-compose.yml
version: '2'

services:
  mail:
    # メールサーバ
    image: djfarrelly/maildev
    ports:
      - "1080:80"
      - "25:25"
    expose:
      - "80"
      - "25"
  db:
    image: mysql:5.7
    command: mysqld --character-set-server=utf8 --collation-server=utf8_unicode_ci
    volumes:
      # ホストOSのディレクトリをゲストOSにマウントする
      # macでの速度改善のためにcachedを入れる
      - ${HOST_OS_DIR}/.data:/var/lib/mysql:cached
      # docker起動時に投入したいDDLやDMLを以下に置く
      - ./db/init:/docker-entrypoint-initdb.d
      # sql_modeをカスタマイズしている
      - ./db/mysqld.cnf:/etc/mysql/mysql.conf.d/mysqld.cnf
    environment:
      MYSQL_ROOT_PASSWORD: "xxx"
      MYSQL_DATABASE: "xxxx"
      MYSQL_USER: "xxx"
      MYSQL_PASSWORD: "xxx"
      MYSQL_HOST: "xxx"
      TZ: "Asia/Tokyo"
      # 任意のパスをホストOSの環境変数に設定する
      # このディレクトリ配下に永続化するデータが置かれる
      HOST_OS_DIR:
    ports:
      - "3307:3306"
    restart: always
  web:
    # Dockerfileを用意する
    build: ./web
    ports:
      - "80:80"
      - "443:443"
    expose:
      - "80"
      - "9000"
    environment:
      TZ: "Asia/Tokyo"
      # 環境を識別する変数
      APPLICATION_ENV: "development"
      HOST_OS_DIR:
    volumes:
      # カスタムしたい設定ファイルはホストOSに作ったファイルで上書き
      - ./web/php.ini:/etc/php.ini
      - ./web/15-xdebug.ini:/etc/php.d/15-xdebug.ini
      - ./web/httpd.conf:/etc/httpd/conf/httpd.conf
      - ./web/ssl.conf:/etc/httpd/conf.d/ssl.conf
      - ./web/vhosts.conf:/etc/httpd/conf.d/vhosts.conf
      - ./web/mysqld.sock:/etc/mysqld.sock
    restart: always
    # docker起動時に必要なコマンドを記述
    command: > 
      bash -c "
        composer install --prefer-dist;
        npm install;
        npm install -g gulp;
        gulp install;
        apachectl -DFOREGROUND;"
```
TSAのまとめ

# チャットボットを作ってみよう（ダイジェスト版）

[Dialogflowでルールベースのチャットボット](https://qiita.com/ume1126/private/62f7796b20b94a0d5317)

</br>
</br>
</br>
</br>
</br>


## Dialogflowでチャットボットを作ってみる

1.　[Dialogflowでチャットボット -準備編](https://qiita.com/ume1126/private/570c2b849c5d0118ff78)
2.　[Dialogflowでチャットボット -エージェント](https://qiita.com/ume1126/private/fa6cfd65b2695dc1cc16)
3.　[Dialogflowでチャットボット -返事をさせる(1)ENTITY](https://qiita.com/ume1126/private/8faa21aa2a921d2fa82e)
4.　[Dialogflowでチャットボット -返事をさせる(2)INTENT](https://qiita.com/ume1126/private/b226498a7896f4b2a1a9)
5.　[Dialogflowでチャットボット -返事をさせる(3)VALUE](https://qiita.com/ume1126/private/c49f74b0f2e3e2cc2f28)
6.　[Dialogflow　でチャットボット -会話の分岐](https://qiita.com/ume1126/items/f60335179b1cee25fa2f#6-%E4%BC%9A%E8%A9%B1%E3%82%92%E3%81%A4%E3%81%AA%E3%81%90)
7.　[Dialogflowでチャットボット -修正する](https://qiita.com/ume1126/private/7a5089985f17621696fd)
8.　[Dialogflowでチャットボット -Slack連携](https://qiita.com/ume1126/private/bddb96755c0f8bdcef25)
9.　[Dialogflowでチャットボット -LINE連携](https://qiita.com/ume1126/private/856e1ca03e58ad952323)
10.　応用編：[Node-RED - API呼び出ししてみる（ぐるなび）](https://qiita.com/egplnt/items/3a6ec71066025108e2ed)(egplntさん)

.　[参考：Dialogflow辞書](https://qiita.com/ume1126/items/7fa08f747a3070fd712f)

</br>
</br>
</br>

## 会話のフロー

チャットボットに何をさせたいのかを考えることが先決です。
また、ここではある程度選択肢を絞ったフローが作りやすいでしょう。
![171127_チャットボットフロー.png](https://qiita-image-store.s3.amazonaws.com/0/192887/2a6b3869-bd07-8690-a875-0a7db8e857dc.png)
OpenCV for Unity でステレオカメラの画像を分割する

# 環境
* Windows 10 64bit
* Unity 2017.2
* VisualStudio 2017
* OpenCV for Unity 2.2.3

# 概要
ステレオカメラをOpenCVで取り込んだ所、以下のように画像が合成されて入力された。
ROI（Region Of Interest）を利用し片側カメラの映像だけ取得したい。

![image](https://qiita-image-store.s3.amazonaws.com/0/163818/d2fe01c4-7716-4cff-5749-c1816ff85837.png)

# 実装
WebCamTextureToMatHelperExampleをベースに作成します。

オリジナルのMat画像から画素アクセスし取得してみた所、処理時間が実用レベルではないほどかかってしまった。

    byte[] test = new byte[4];
    Mat leftMat = new Mat(rgbaMat.rows(), rgbaMat.cols() / 2, CvType.CV_8UC4);
    for (int i = 0; i < leftMat.rows(); i++)
    {
        for (int j = 0; j < leftMat.cols(); j++)
        {
            rgbaMat.get(i, j, test);
            leftMat.put(i, j, test);
        }
    }
    
    
OpenCVのRectを使用してみた。
以下のように実装。C++でのOpenCVの書き方とは少し変わります。

    OpenCVForUnity.Rect roi = new OpenCVForUnity.Rect(0, 0, rgbaMat.cols() / 2, rgbaMat.rows());
    Mat leftMat = new Mat(rgbaMat, roi);

処理時間は1ms以下になりました。
bash > fileIO > ファイルから変数の値を読む実装 > export $elem=$value 使用

```txt:動作環境
Xeon E5-2620 v4 (8コア) x 2
32GB RAM
CentOS 6.8 (64bit)
openmpi-1.8.x86_64 とその-devel
mpich.x86_64 3.1-5.el6とその-devel
gcc version 4.4.7 (とgfortran)
NCAR Command Language Version 6.3.0
WRF v3.7.1を使用。
Python 2.6.6 (r266:84292, Aug 18 2016, 15:13:37) 
Python 3.6.0 on virtualenv
```

### 処理内容

```position_171124.txt
POS0_LAT:34.1
POS0_LON:135.1
```

上記のファイルから値を、それぞれ変数`POS0_LAT`と変数`POS0_LON`に読込む。

### code v0.1

```bash:read_file_171124_exec
#!/usr/bin/env bash

IN_FILE=position_171124.txt

keys=$(cat $IN_FILE | tr ":" " " | awk '{print $1}')
#echo $keys

for elem in $keys;do
	# echo $elem
	value=$(cat $IN_FILE | grep $elem | tr ":" " " | awk '{print $2}')
	export $elem=$value
done

echo "POS0_LAT=" $POS0_LAT
echo "POS0_LON=" $POS0_LON
```

```bash
$ bash read_file_171124_exec 
POS0_LAT= 34.1
POS0_LON= 135.1
```

### 備考

以下だと`command not found`になる。

```
$elem=$value
```

exportを追加した。

```
export $elem=$value
```

### 考慮点1

position_171124.txtから変数の値を読むことで、以下の利点がある。

- bash scriptを変更しなくてよい
- 処理記録として残すことができる

別の方法として、実行時引数とする方法もあるが、その場合は、「実行記録」を別途作らないと「何を処理したか」の記録が残らない。

### 考慮点2

position_171124.txtそのものに変数名を持たせることで、単独ファイルでの閲覧性が高まる。

以下のようにするのでも良いかもしれない。

```position_171124.txt
34.1   #POS0_LAT
135.1  #POS0_LON
```

### code v0.2

関数化した。

```bash:read_file_171124_exec
#!/usr/bin/env bash

read_latlon()
{
	IN_FILE=position_171124.txt

	keys=$(cat $IN_FILE | tr ":" " " | awk '{print $1}')
	#echo $keys

	for elem in $keys;do
		# echo $elem
		value=$(cat $IN_FILE | grep $elem | tr ":" " " | awk '{print $2}')
		export $elem=$value
	done
}

read_latlon

echo "POS0_LAT=" $POS0_LAT
echo "POS0_LON=" $POS0_LON
```
シート上のデータを配列に格納する際、一意になるように格納する方法

シート上のデータを配列に格納する際、『すでに格納済みのデータは除外したい』ということがあるかと思います。
そんなときに便利なDictionaryというオブジェクトを紹介します。


```vbnet
    'セルに記載されている値を一意に配列に格納する

    Dim dic_test   As Object
    Dim arg_test() As String
    Dim cnt_test   As Long
    Dim i          As Long

    'Dictionaryオブジェクト生成
    Set dic_test = CreateObject("Scripting.Dictionary")
    
    'A1セルからA100セルまで処理
    i = 0
    Do
        i = i + 1
        If i > 100 Then
            Exit Do
        End If
            
        'キー値セット
        key = Cells(i, 1).Value
    
        'キー値がDictionary内に存在しないときのみ、配列に登録
        If dic_test.exists(CStr(key)) = True Then
        Else
            'キー値をディクショナリに追加
            dic_test.Add CStr(key), ""
            
            cnt_test = cnt_test + 1
            ReDim Preserve arg_test(1 To cnt_test)
            arg_test(cnt_test) = key
        
        End If
    
    Loop

    'この時点のarg_testは、A1セルからA100セルの値を、一意になるように登録されている
```

ポイントは、キー値の判定の際、変数の型によって判定できないことを防ぐため、CStrを使用して必ず文字列型のキー値として判定しているところです。

Dictionaryオブジェクトの検索はとっても速いので、配列をループして存在確認するより速いです。（要素数が増えれば増えるほど実感できます。）
boto3 でオブジェクトを JSON に変換

boto3 (AWS SDK for Python) で、オブジェクトを JSON に変換する方法です。　json.dumps(response) だと、datetime 型に対応していません。

参考にしたページ
[boto3 (AWS SDK for Python) メモ](https://qiita.com/draco/items/8b99e5494ec5b1371f32)

Arch Linux で、bson のインストール

```bash
sudo pacman -S python-pymongo
```

Ubuntu 17.10 で、bson のインストール

```bash
sudo apt install python3-pymongo
```

```py3:boto3_json.py
#! /usr/bin/python
# -*- coding: utf-8 -*-
#
#	boto3_json.py
#
#						Nov/24/2017
#
import sys
import json
import boto3
from bson import json_util
# --------------------------------------------------------------------
sys.stderr.write("*** 開始 ***\n")

client = boto3.client('ec2')
response = client.describe_instances()
print(type(response))

res_json = json.dumps(response, default=json_util.default)
print(type(res_json))

print(res_json)
sys.stderr.write("*** 終了 ***\n")
# --------------------------------------------------------------------
```

参考
Raspbian での　boto3 のインストール

```bash
sudo pip3 install boto3
```
GoとCの間のポインタ渡し

これは[Go3 Advent Calendar 2017](https://qiita.com/advent-calendar/2017/go3)の3日目の記事です。

CでGOのポインタを扱う方法と、GoでCのポインタを扱う方法を紹介する。

コードは以下にあります。

https://github.com/74th/adventcalendar2017-go3-4

## GoのポインタをCで扱う場合

そのままGoのポインタを渡すコードを作成すると、ビルドエラーになる

```go:libgo2c.go
import "C"

//export createGoInstancePointer
func createGoInstancePointer(n C.int) *box {
	b := new(box)
	b.content = int(n)
	return b
}
```

```
go build -buildmode=c-shared -o libgo2c.so go2c.go
Go type not supported in export: struct
```

unsafe.Pointerにしてから渡すコードを作成すると、ビルドできるが、実行時エラーになる

```go:libgo2c.go
import "C"

//export createGoInstanceUnsafe
func createGoInstanceUnsafe(n C.int) unsafe.Pointer {
	b := new(box)
	b.content = int(n)
	return unsafe.Pointer(b)
}
```

```c:main.c
void *unsafeBox = createGoInstanceUnsafe();
```

```
go build -buildmode=c-shared -o libgo2c.so go2c.go
gcc -o main main.c -I./ -L./ -lgo2c
panic: runtime error: cgo result has Go pointer
```

unsafe.Pointer->uintptrに変換すると、渡すことができる

```go:libgo2c.go
import "C"

// ガベージコレクションで削除されないように、
// グローバル変数とつなげておくための補完先
var boxInstances map[uintptr]*box

//export createGoInstanceUintptr
func createGoInstanceUintptr(n C.int) uintptr {
	b := new(box)
	b.content = int(n)
	p := uintptr(unsafe.Pointer(b))

	if boxInstances == nil {
		boxInstances = make(map[uintptr]*box)
	}
	boxInstances[p] = b

	return p
}
```

もちろんuintptrを、unsafe.Pointer経由で元の型に復元できる

```go:libgo2c.go
//export getBoxContents
func getBoxContents(p uintptr) C.int {
	b := (*box)(unsafe.Pointer(p))
	return C.int(b.content)
}
```

## Goのバイト列をCで扱う場合

Goのバイト列の先頭のポインタをCに渡すことで、CでGoのバイト列を扱うことができる

```go:libc2go.go
import "C"

var buffer []byte

//export getGoBytes
func getGoBytes() uintptr {
	buffer = []byte("GoBytes\x00")
	return uintptr(unsafe.Pointer(&buffer[0]))
}
```

```c:main.c
char *gobyte = (char *)getGoBytes();
printf("go string:%s\n", gobyte);
```

## CのポインタをGOで扱う場合

簡単なCのライブラリのコードを示す

```c:libc2go.h
typedef struct{
	int content;
} box;

box *createCInstance(int n);
```

```c:libc2go.c
#include <stdio.h>
#include "libc2go.h"

box *createCInstance(int n)
{
	box *b = malloc(sizeof(box));
	b->content = n;
	return b;
}
```

Goのコード中にCのライブラリを参照するのLDFLAGSを追記する
GoはCのポインタを扱うことができる

```go:c2go.go
// #cgo LDFLAGS: -L./ -lc2go
// #include "libc2go.h"
import "C"

func main() {
	b := C.createCInstance(42)
	fmt.Printf("c pointer:%p\n", b)
	fmt.Printf("c struct contents:%d\n", int(b.content))
}
```

```sh
gcc -shared -fPIC -o libc2go.so libc2go.c
go run c2go.go
c pointer:0x4202900
c struct contents:42
```

## Cのバイト列をGoで扱う場合

C.GoString()を使うことで変換できるが、コピーが行われる。
直接参照するためには、unsafe.Pointer->固定長配列のポインタ->スライスの順に変換を行う

```go:c2go.go
// char *getCByte()
cbyte := C.getCByte()

fmt.Printf("GoString():%s\n", C.GoString(cbyte))

// 1.unsafe.Pointerに変換
cbytePointer := unsafe.Pointer(cbyte)
// 2.固定長の配列のポインタに変換
cbyteArray := (*[1024]byte)(cbytePointer)
// 3.スライスに変換
cbyteSlice := cbyteArray[:7]
// cのバイト列をそのままスライスとして利用
fmt.Printf("cbyteSlice():%s\n", cbyteSlice)
```

```
gcc -shared -fPIC -o libc2go.so libc2go.c
go run c2go.go
GoString():CByte
cbyteSlice():CByte
```
FuelPHPのバリデーション実行順序

# はじめに
先月からPHP/FuelPHPを使うことになって色々勉強しながら実装中。
その中で、特にFuelPHP周りの機能や挙動について調べたことをメモとして残していきます。
※PHP7.1.9/FuelPHP1.8を使用

# Validationクラス
バリデーションの仕組みを提供するクラス。名前まんま。
Fieldsetから入ったので最初は戸惑ったが、ValidationはValidationでフィールド定義を内部で保持していて（validation->fields）、それぞれについてどのバリデーションを実行するか（field->rules）を管理している模様。

# runメソッド
バリデーションを実行する。引数を指定すればその値に対してバリデーションを実行。なければInput::param()を使うみたい。
前項で書いたとおりFieldsetから入ったので「なんでFieldset::forgeするときにパラメータ渡してるのに、runすると渡したパラメータが無視されてるんだ？？？」て悩んでたけど、そういう仕様だと分かれば問題はない。

# 複数の「バリデーション済みのフィールド」を参照したい
カスタムバリデーションを実装するとき、複数のフィールドの値を参照したバリデーションを作りたい…というのはよくあること。
バリデーションメソッドの中から他のフィールドの値を参照する方法を調べていたところ、`Validation::active()->input()`を使えばいいらしい…のだけど、ちょっと待って。
個別の入力フィールドにはそれぞれrequiredやmax_length等々をadd_ruleしてるわけで、カスタムバリデーションはそれらが全てパスしてる前提で書いている。
さらに調べてみたところ、`Validation::active()->validated()`を使えば、バリデーション済みの値だけが取れる（エラーが検出されたフィールドは入ってこない）ようだけど…そもそもカスタムバリデーション実行時点で、個別のバリデーションが完了している保障はあるのか？

# バリデーションはaddした順番に実行される
そんなわけでFWのソースを追いかけてみたところ、以下のような処理になっていた。

```php:fuel/core/classes/validation.php(line346-389,runメソッドの実装)
		$this->validated = array();
		$this->errors = array();
		$this->input = $input ?: array();
		$fields = $this->field(null, true);
		foreach($fields as $field)
		{
			static::set_active_field($field);

			// convert form field array's to Fuel dotted notation
			$name = str_replace(array('[', ']'), array('.', ''), $field->name);

			$value = $this->input($name);
			if (($allow_partial === true and $value === null)
				or (is_array($allow_partial) and ! in_array($field->name, $allow_partial)))
			{
				continue;
			}
			try
			{
				foreach ($field->rules as $rule)
				{
					$callback  = $rule[0];
					$params    = $rule[1];
					$this->_run_rule($callback, $value, $params, $field);
				}
				if (strpos($name, '.') !== false)
				{
					\Arr::set($this->validated, $name, $value);
				}
				else
				{
					$this->validated[$name] = $value;
				}
			}
			catch (Validation_Error $v)
			{
				$this->errors[$field->name] = $v;

				if($field->fieldset())
				{
					$field->fieldset()->Validation()->add_error($field->name, $v);
				}
			}
		}
```

`$validation->fields`を先頭から処理、fieldごとに`$field->rules`を先頭から処理…という素直な構造。
要するに、addした順番に実行してくれるわけですね。そして、validatedに値が格納されるのは、そのfieldに定義されたバリデーションが全てパスしてから…となる。

# カスタムバリデーションはどこでaddする？
フィールド内で閉じたバリデーションであれば、そのフィールドにadd_ruleすればOK。
複数フィールドを参照するものは、前提となるfield/ruleをaddし終えてからaddする。このとき、実際のfieldに対してaddするよりかは、バリデーション用のダミーのfieldを最後にaddして、そこにカスタムバリデーションをまとめてadd_ruleするのがいいかも？

実際にはFieldsetを介して操作することになるので、以下のような実装に落ち着いた。

```php:example.php
$fieldset = Fieldset::forge('form_id');
$fieldset->add(/*field1*/)
         ->add(/*field2*/)
         ->add(/*field3*/)
;
$fieldset->validation()->add_callable('custom_validation_class');
$fieldset->validation()->add('dummy_field', 'label', [], [
        ['custom_validation1',/*'param1','param2',...*/],
        ['custom_validation2',/*'param1','param2',...*/],
    ]);
```

ちなみに、単一のフィールドに複数ルールをaddした場合、途中でエラーが検出されると以降のルールは処理されず、次のフィールドのバリデーションへ移行する。
ので、複数のカスタムバリデーションをaddするとき、それぞれのエラーメッセージを出したい場合は、ダミーのfieldを複数addして、それぞれにぶら下げる必要があるので注意。

このへん、ちょっとコードがダサいので、もう少し何とかならないものか…
Compute EngineでIntel® Performance Librariesが無料で利用できるようになったので試してみた

以下のブログポストでIntel Performance Librariesが無料で利用できるようになった旨のアナウンスがあったので、どのようにして利用できるか試してみた。
https://cloudplatform.googleblog.com/2017/11/Intel-performance-libraries-and-python-distribution-enhance-performance-and-scaling-of-Intel-Xeon-Scalable-processors-on-GCP.html

環境： 
- Google Compute Engine
- OS: CentOS 7

yum-config-managerコマンドを使用するので、yum-utilsをインストールする。

```
$ sudo yum -y install yum-utils
```

### Repositoryの追加
MKLのみ追加する場合は以下のコマンドを実行する。

```
sudo yum-config-manager --add-repo https://yum.repos.intel.com/mkl/setup/intel-mkl.repo
```

GPG Keyをインストールする。

```
sudo rpm --import https://yum.repos.intel.com/intel-gpg-keys/GPG-PUB-KEY-INTEL-SW-PRODUCTS-2019.PUB
```

### MKLをインストール

```
sudo yum install intel-mkl-2017.3-056
```

/opt/intel/mklのディレクトリが作成されていることを確認できるので、
これでMKLのライブラリーが利用できる。

### 参考
個別のパッケージではなく全部(ippやdaalなど)追加したい場合は以下のようにする。

```
sudo yum-config-manager --add-repo https://yum.repos.intel.com/setup/intelproducts.repo
```

詳細は公式ページを参照
https://software.intel.com/en-us/articles/installing-intel-free-libs-and-python-apt-repo

Debianなどの環境で、apt-getを利用してinstallする場合は以下を参照
https://software.intel.com/en-us/articles/installing-intel-free-libs-and-python-apt-repo
Unity C#で処理時間を計測する

# 環境
* Unity 2017.2
* VisualStudio 2015
* Windows 10 64bit

# 実装
UnityにはSystem.Diagnostics.Stopwatchというクラスが用意されています。
これを使用し、時間を計測します。

今回はなぜかネームスペースをusingで呼び出した場合、Debugというクラスが重複してしまうようで、エラーが出てしまいました。
ですので以下のように記述します。

    System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch();
    sw.Start();
    for(int i = 0; i < 60000; i ++){
        for(int j = 0; j < 60000; j++){
        }
    }
    sw.Stop();
    Debug.Log(sw.ElapsedMilliseconds + "ms")
    
これでコンソールに処理時間が表示されます。
ElapsedMillisecondsの戻値はlongです。
react-routerでページ遷移後にページ最上部から表示する

# 概要
* react-routedeページ遷移時、`window.scrollTo(0, 0)`を実行できるような仕組みにすればOK

# 仕組み導入前後
新規itemの作成後、react-routerの機能を使って、item画面に遷移するアプリを想定。
react-routerはヘッダー以外の部分を描画するので、何も対策しないと、ヘッダー以外の部分が表示されます。（以下のような感じ）

```app/javascript/containers/App.jsx
import React from 'react'
import {MuiThemeProvider} from 'material-ui/styles';
import theme from '../assets/theme'
import {BrowserRouter, Switch, Route} from 'react-router-dom';
import Home from './Home'
import About from './About'
import Header from './Header'
import Item from './Item'

class App extends React.Component {
  render() {
    return (
      <MuiThemeProvider theme={theme}>
        <BrowserRouter>
          <div>
            <Header/>
            <Switch>
              <Route exact path={'/'} component={Home}/>
              <Route exact path={'/items/:token'} component={Item}/>
              <Route path={'/about'} component={About}/>
            </Switch>
          </div>
        </BrowserRouter>
      </MuiThemeProvider>
    )
  }
}

export default App

```

* 仕組み導入前
item画面に遷移したとき青色のヘッダーが見えなくなっているのがわかります。

[![https://gyazo.com/fa992e00974683662ac377e6fd04c4b5](https://i.gyazo.com/fa992e00974683662ac377e6fd04c4b5.gif)](https://gyazo.com/fa992e00974683662ac377e6fd04c4b5)

* 仕組み導入後

item画面に遷移したとき青色のヘッダーから期待通り表示されているのがわかります。

[![https://gyazo.com/21c9bb137aa6d99e3daa15b58825e401](https://i.gyazo.com/21c9bb137aa6d99e3daa15b58825e401.gif)](https://gyazo.com/21c9bb137aa6d99e3daa15b58825e401)

# 方法
[公式](https://reacttraining.com/react-router/web/guides/scroll-restoration)の手法のまま。
1. `window.scrollTo(0, 0)`を実行するcomponent（`<ScrollToTopOnMount/>`）を作成
2. ページ遷移後、ページ最上部に移動させたいcontainerに`<ScrollToTopOnMount/>`を追加する

## <ScrollToTopOnMount/>component作成
読み込み時、`componentDidMount`を使って、最上部にスクロールするjavascriptのコード`window.scrollTo(0, 0)`を実行するcomponentを作成する。

```app/javascript/containers/ScrollToTopOnMount.jsx
import React from 'react'

export default class ScrollToTopOnMount extends React.Component {
  componentDidMount(prevProps) {
    window.scrollTo(0, 0)
  }

  render() {
    return null
  }
}
```

## 作ったcomponentを組み込む
上記で作成したcomponent`<ScrollToTopOnMount/>`を使いたいページ（ここでは、`Item.jsx`）に追加するだけ。

```app/javascript/containers/Item.jsx
import React from 'react'
class Item extends React.Component {
  render() {
    return (
      <div>
        <ScrollToTopOnMount/> //これを追加するだけ。
        <ItemTopCard/>
      </div>
    )
  }
}


export default withStyles(style)(Item)

```

以上。
Cloud Functions for Firebase でCORSを許可する方法

割とCORSを使用したいシチュエーションは多いのではないかと思い共有。
そもそものCloud Functionsの使い方が分からない方は[こちら](https://firebase.google.com/docs/functions/get-started?hl=ja)を参照してみてください。

[expressのcorsパッケージ](https://github.com/expressjs/cors)を使うことによって実現します。

上記パッケージを `npm install cors` もしくは `yarn add cors` でインストールして、CORSを許可したい関数を以下のようにwrapします。

```js:index.js
const functions = require('firebase-functions');
//importする際に　{origin: true}　をつける
//もう少し詳細に指定したい場合はこちらをご参照ください https://github.com/expressjs/cors#configuration-options
const cors = require('cors')({origin: true});

exports.withcors = functions.https.onRequest((request, response) => {
  //関数内全体をwrap
　cors(request, response, () => {
    response.status(200).send('success！');
  });
});
```

すごい短くなってしまいましたが、ご覧の通り簡単に実現できるので困ったらお試しください。
PHP 5.6.xから7.0.xに移行におけるコード修正


### まだ途中なので随時更新します。

# 概要
最近バージョンが別のものを扱うことが多いため、バージョンによっての変更点などをまとめようと思い至った。詳しい変更点などは公式のドキュメントに任せることとしてコードベースでどのような点を直したら良いかをまとめる。ただし、「動作を変わらないように動かす」という点に重きを置いているため、ベストプラクティスではないことも多いことに注意。


**もし良い方法をお持ちの方はご教授お願いしますm(_ _)m**

# 対象

- 現在PHP5.6以前でコードを書いている方


# 動かなくなるコードを今までと同じように動作させる
## その１ 「$$」 => 「global は単純な変数だけを受け付ける」

今まで動いていた「$$変数」が動かなくなるので以下のように変更する。
また、この使い方は5.6でも使えるのでもし5.6.xをまだ使っている方がいれば、先に変更しておくとのちの移行で捗ると思われる。

```php:index.php
<?php
function f() {
    // PHP 5 でしか使えません
    global $$foo->bar;

    // PHP 5 と PHP 7 の両方で使えます
    global ${$foo->bar};
}
?>
```

> 一般論として、単純な変数以外を global で使うことは推奨しません。


## 変更点その２ 「set_exception_handler」

set_exception_handler() で登録した例外ハンドラの実装で Exception 型を宣言している場合は、 Error オブジェクトがスローされると fatal エラーが発生

```php:error.php
<?php
// PHP 5 でのこの実装は、そのままでは PHP 7 では動きません
function handler(Exception $e) { ... }
set_exception_handler('handler');

// PHP 5 と 7 の両方で動く
function handler($e) { ... }

// PHP 7 でだけ動く
function handler(Throwable $e) { ... }
?>
```



## その３ 「global は単純な変数だけを受け付ける」

```php:global_variable.php
<?php
function f() {
    // PHP 5 でしか使えない
    global $$foo->bar;

    // PHP 5 と PHP 7 の両方で使える
    global ${$foo->bar};
}
?>
```


# 動くけれど、落とし穴になりそうな点

## その１ 「list()の挙動変更」

**list() での変数の代入が、逆順ではなくなる**
これは今までとは違う挙動になるので注意が必要。
listを使っていた場合にはそこの挙動をチェックして影響の確認が必要。


```php:list.php
<?php
list($a[], $a[], $a[]) = [1, 2, 3];
var_dump($a);
?>
```

```php:PHP5の出力
array(3) {
  [0] => int(3)
  [1] => int(2)
  [2] => int(1)
}
```

```php:PHP7の出力
array(3) {
  [0] => int(1)
  [1] => int(2)
  [2] => int(3)
}
```


> 一般論として、 list() での代入がどの順で行われるかに依存するコードは書かないことを推奨します。 代入の順番は、実装の都合によって今後も変わる可能性があるからです。

と公式ドキュメントには書かれているため、listの順番に関わるコードを書いていてそれを置き換える際には、とりあえず動かしたいなら、sortあたりでよしなにしてあげると良いかもしれない。(冗長になりそう)

## その2 「空の list() の廃止」

今まではできていた空のlistでの定義ができなくなった。
よって、以下のようなコードはphp7では動かない。

```php:empty_list.php
<?php
list() = $a;
list(,,) = $a;
list($x, list(), $y) = $a;
?>
```

もし上記のようなlistがあれば、空のlistではない初期化を利用する。


## その3 「list() は文字列を展開しない」

PHP7からはlist() が文字列変数を展開しない。 また、以下では参照わたしも使っているが、これも注意が必要な模様。

```php:str_list.php
<?php
list($bar) = "abcde";
var_dump($bar); // NULL
?>
```

PHP7から動かすには[str_split](http://php.net/manual/ja/function.str-split.php)(文字列を配列にする) を使うと良い。公式でもその方法を推奨している模様。

```php:fix_str_list.php
<?php

$str = "abcde";

$arr1 = str_split($str);
$arr2 = str_split($str, 3);

print_r($arr1);
print_r($arr2);

?>
```

```
Array
(
    [0] => H
    [1] => e
    [2] => l
    [3] => l
    [4] => o
    [5] =>
    [6] => F
    [7] => r
    [8] => i
    [9] => e
    [10] => n
    [11] => d
)

Array
(
    [0] => Hel
    [1] => lo
    [2] => Fri
    [3] => end
)
```

### 注意点

**str_split() でのマルチバイト文字列の扱いは、文字単位ではなくバイト単位での分割となる**

## 参照による代入で自動的に作成した配列要素の並び順の変更

```php:list.php
<?php
$array = [];
$array["a"] =& $array["b"];
$array["b"] = 1;
var_dump($array);
?>
```

```php:PHP5
array(2) {
  ["b"] => &int(1)
  ["a"] => &int(1)
}
```

```php:PHP7
array(2) {
  ["a"] => &int(1)
  ["b"] => &int(1)
}
```

```php:fix_str_list.php
<?php
$array = [];
$array["a"] =& $array["b"];
$array["b"] = 1;
var_dump($array);
?>
```
Railsアプリケーションのwheneverタスク起動でspringがメモリ食いまくってサーバ死亡する

# 主旨

よろしければどなたか教えてください。

# 問題

railsアプリケーションを運用しているサーバがメモリ不足で死ぬことがある。
私はrails初心者なので、原因というか障害の成り立ちがよく分からずヤバイ。
springというのもよく分かってない。

# 主な環境
rbenv local で ruby 2.4.2を使用。
rails5.1.4を使用。
unicorn を使用。
whenever を使用。
30分ごとにTwitterに投稿、TwitterAPIを叩ける限り叩く、ちょい時間かかるタスクをwheneverで登録。
Twitterへのつぶやきの内容を編集するviewも用意し、使用している。
以下、railsアプリケーションのルートディレクトリは「/rails_root」とする。

# 症状

`rbenv exec bundle exec unicorn_rails -c config/unicorn.rb -D -E production`起動後、htopで見るとrails関係のプロセスはこれだけ（のはず）。

![1.png](https://qiita-image-store.s3.amazonaws.com/0/1642/edb9d700-eaf9-651f-91d2-741c81094c4f.png)

30分ごとのwheneverタスクが起動すると、こういうのが追加される。

![2.png](https://qiita-image-store.s3.amazonaws.com/0/1642/0569c333-a9f8-edb2-7aa7-91787dfad7a0.png)

wheneverタスクが終了しても、これだけは残存している。

時間を経るごとに、`spring app`の部分が徐々に増えていって、MEM%4.Xぐらいのプロセスがたくさんになって、数日のうちにサーバが死亡してしまう。

また、`spring app`を放置して数日過ごしていると、

- wheneverタスクは動くがviewが503になってしまう
- viewは使えるが、wheneverタスクがたくさん詰まってメモリ食いまくってサーバ死亡

のいずれかのパターンに陥る。

# 対策1

なので30分ごとのタスクとかぶらないタイミングで1時間ごとに、以下のようなcronジョブでunicornを再起動するようにしている。

```shell-session:cron_job
cd /rails_root
hg pull
hg update -C tip
rbenv exec rake assets:precompile RAILS_ENV=production
bundle exec whenever --update-crontab RAILS_ENV=production
spring stop
kill -9 `cat /rails_root/tmp/pids/unicorn.pid`
rbenv exec bundle exec unicorn_rails -c config/unicorn.rb -D -E production
```

肝心なのは`spring stop`のところで、これによりメモリ食いまくりプロセスが全滅する。
これで事なきを得ているような気がするが、こんな運用はそもそもおかしいと思うし、みんなやってないと思う。
どうしてこうなるのか、どうするべきなのかなどをご存知の方がいらっしゃいましたら、ぜひ教えていただきたいです。

# 対策2

先述の対策1ではうまくいかなかったので、アプリケーションからspringを削除してみた。

こちらの削除方法を用いた。
http://ruby-rails.hatenadiary.com/entry/20141026/1414289421#spring-removal

`bin/spring binstub --remove --all`
Gemfile から `gem 'spring'`をコメントアウト。
`rbenv exec bundle install`

これでwheneverタスク実行時にspringプロセスは出なくなった。
しかしspringはrailsコマンド実行を高速化する良い機能であるという。
そういったものを止める、というネガティヴな解決方法は遺憾だが、動かなくなるよりはマシなので、より良い方法を見つけるまでは、これで様子を見たい。

## 心当たり

`whenever --update-crontab`すると`rails runner`とかcrontabに書きこむが、railsコマンドに関連づいているサーバソフトがunicornではないからこうなってるんじゃないかという気がする。
単に`rails s`を実行すると、pumaというサーバソフトが起動する。unicornではない。
この辺のしくみがよく分からない。

## 予後

springを削除したら、当然ながらプロセスにspringが出現しなくなり、viewの表示、wheneverによるcronタスク共に安定した。
めでたし。
MATLAB > [v,~,idx] = unique(v,'rows'); > tilde(~):プレースホルダ > Pythonでの下線(_)に相当するのだろう

```txt:動作環境
GeForce GTX 1070 (8GB)
ASRock Z170M Pro4S [Intel Z170chipset]
Ubuntu 16.04 LTS desktop amd64
TensorFlow v1.2.1
cuDNN v5.1 for Linux
CUDA v8.0
Python 3.5.2
IPython 6.0.0 -- An enhanced Interactive Python.
gcc (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
GNU bash, version 4.3.48(1)-release (x86_64-pc-linux-gnu)
scipy v0.19.1
geopandas v0.3.0
MATLAB R2017b (Home Edition)
```

### MATLAB

```matlab
[v,~,idx] = unique(v,'rows');
```

https://jp.mathworks.com/help/matlab/ref/unique.html
> [C,ia,ic] = unique(A,'rows') は、C = A(ia,:) かつ A = C(ic,:) となるようなインデックス ベクトル ia および ic も返します。

tildeの方はどういう意味か。
https://jp.mathworks.com/help/matlab/matlab_prog/matlab-operators-and-special-characters.html
> 引数のプレースホルダー
> ...
> チルダ記号を使用して、論理否定を表現したり、特定の出力引数の出力を抑制したりします。

Pythonでの以下のような書き方(_:下線)に相当するのだろう。

```
v, _, idx = 関数()
```

### 検索用キーワード

- placeholder
Windows 10 S(Fall Creators Update)検証 

## 前情報

### ライセンス

[Windows 10 S の新規インストールがFall Creators Updateで可能に - パソコンりかばり堂本舗](https://www.ikt-s.com/windows-10s-install/#i-3)

* Windows 10 Pro のライセンスが必要 (27,864円)


### 10 Pro に切り替えが可能

[Windows 10 SをPro版にエディションアップする手順 | Ask for Windows](http://www.ask-mswin.com/win10-10s-upgrade/)


### 10 S は誰が使うの？

ローカルのexeが使えないため、セキュリティを担保したい企業向けに需要があると見込まれる。

----

## クリーンインストールしてみた

* `Windows 10 Fall Creators Update`から`Windows 10 S`もインストールの選択ができるようになった。
* インストールの流れ
    * Homeと同じ
    * ユーザーはオフラインアカウントでも作成可能
    * インターネットに繋がっていなくてもセットアップ完了できる
* 使用DISK容量
    * 11.8GB程度。60GBのHDDにインストール。トラブルなく完了した。

### 32bit版 Internet Explorerの起動

* `C:\Program Files (x86)\Internet Explorer\iexplorer.exe`の実行で起動できました。
* ActiveXはインストール成功しない。
    * 「インストールしますか？」で「はい」を押してもインストールされていない。（リロードの度に聞いてくる。）
* Flashは動く

### exe

* .exeは動かない。
    * 動かそうとするとProにアップグレードページが表示される。
    * 自己解凍型書庫も解凍できない。
    * `cmd.exe` も実行できない。.batが実行できない。
    * `Wscript.exe`も`cscript.exe`も実行できないため.vbsは実行できない。
    * regedit.exeも実行できない。
* pathping.exeは動く。

* diskpart.exeは「ファイル名を指定して実行」から実行できた。
* c:\windows\system32\cmd.exe をデスクトップにコピーしてdiskpart.exeにリネームして実行してもだめだった。
* UserAgentは他のwindows10と同じだった。(特徴的な文字の追加があるかと思ったがなかった。)

| プログラム| 通常 | セーフモードで動くか |
|:--|:--|:--|
| cmd.exe | × | ○ |
| Wscript.exe | × | ○ |
| regedit.exe | × | ○ |
| pathing.exe | ○ | ○ |
| よそから持ってきたexe | × | × |

regedit.exeで登録したレジストリはOSを通常したあとはもとに戻っていた。


### USBメモリ

* 違和感なく読み書き可能

### トラブルシューティングからのコマンドプロンプト

* 起動できた。再起動時にShiftキーを押しながら再起動で

[Windows 8.1 で Windows が起動できない場合のデータのバックアップ方法 - マイクロソフト コミュニティ](https://answers.microsoft.com/ja-jp/windows/forum/windows8_1-system/windows-81-%E3%81%A7-windows/7a24de51-073b-4f21-bf68-0c474c16f7ea?auth=1)のような画面となる。

```
d:
cd \Users\username\Downloads
```

ここでダウンロードしてきたexeを実行できるか確認したところ、以下出力で実行できない。

> このバージョンのD:\Users\username\Downloads\a.exe は、実行中の Windows のバージョンと互換性がありません。コンピューターのシステム情報を確認してから、ソフトウェアの発行元に問い合わせて下さい。

ここからの vbscript や .bat は実行できた。
diskpart.exeも実行可能

### Windows Updateサービスの停止

普通に停止できた。


### Windows Subsystem for Linuxは利用できなかった。

`Windowsの機能の有効化または無効化`からインストール。OS再起動
Storeで`Ubuntu`をインストール。（190MB程のダウンロード）

```sh:エラーで利用できなかった。
Installing, this may take a few minutes...
Installation successful!
Please create a default UNIX user account. This username does not need to match your Windows username.
For more information visit: https://aka.ms/wslusers
Enter new UNIX username: hoge
Error: 0x80073d07
Press any key to continue...
```


### ダウンロードしたzipの中にあるショートカットがそのままでは実行できない

* https://support.microsoft.com/ja-jp/help/884237

![](https://support.microsoft.com/library/images/support/kbgraphics/public/ja/sp2_884237_03.gif)

「許可する」をクリックする必要がある。(ブロックの解除から名前が変わった。)

### ストア版TeamViewer

* 操作する側にはなれるが、操作される側にはなれない。

### ストア版Google

* chromeベースかと思ったが、Edgeベースだった。
AtCoderをゆっくり解く ABC079A編

[問題はこちら](https://abc079.contest.atcoder.jp/tasks/abc079_a)

4桁の数字が与えられるので、3桁以上の同じ数字が並ぶ「良い数字」か判定しなさい、という問題です。

PHPの場合、標準入力から1つだけ整数を受け取るには、以下のように書きます。

```php
<?php
    fscanf(STDIN, "%d", $N);
```
fscanfは何かしらの値を取ってくる命令。
第1引数のSTDINはSTanDard INputの略で、標準入力。
第2引数の"%d"のdはDecimal(数値)。文字列を受け取りたいときは"%s"とします。(Stringのs）
第3引数は取得した値を受け取る変数。

なので、$Nに入力された値が入ります。

そして……整数を受け取りましたが、これを文字列に直したいと思います。

```php
$S = strval($N);
```

さらに、その文字列を配列にします。

```php
$arr = str_split($S);
```

4桁の数字を受け取って、3桁以上の数字が連続して同じかどうかを判定する問題です。
このとき、3桁の数字が連続して同じになるのは、以下の2通りです。

* 1桁目と2桁目と3桁目の数字が同じ。 …(A)
* 2桁目と3桁目と4桁目の数字が同じ。 …(B)

この2通りのみです。(A)のとき、3桁目と4桁目も同じかは気にしないこととします。
(B)のとき、1桁目と2桁目も同じかも気にしません。

上記の条件をプログラムに書き直します。

```php
if ($arr[0] === $arr[1] && $arr[1] === $arr[2]) {
    echo "Yes\n";
    exit;
}
if ($arr[1] === $arr[2] && $arr[2] === $arr[3]) {
    echo "Yes\n";
    exit;
}
```

if文は、括弧の中の条件文が成立しているかどうかを見ます。
2つのif文は成立した段階で「Yes(改行)」と出力して終わらせるため、直後に「exit;」を記述しています。
（ `exit;` は、プログラムの実行をそこで終了する、という命令です。）
そうしないと、4桁の数字がすべて同じ場合（"1111"とか"5555"とか）に、「Yes(改行)」が2つ表示されてしまい、不正解になります。

最後に、上記2つの条件が成立しなかった場合は、「良い整数」ではないので、「No(改行)」を出力します。

```php
echo "No\n";
```

これが最後の表示なので、「exit;」は不要です。

プログラムをまとめると、以下のようになります。

```php
<?php
    fscanf(STDIN, "%d", $N);
    $S = strval($N);
    $arr = str_split($S);

    if ($arr[0] === $arr[1] && $arr[1] === $arr[2]) {
        echo "Yes\n";
        exit;
    }

    if ($arr[1] === $arr[2] && $arr[2] === $arr[3]) {
        echo "Yes\n";
        exit;
    }
    echo "No\n";
```

最後に、上記のコードをテスト実行してみましょう。環境を用意するのが面倒な場合は、paiza.ioなんかを使うと良いでしょう。

[URL](https://paiza.io/projects/zYJ8QyYZjpzzFyJT2j-x7A)貼っときます。

入力例は「1118」「7777」「1234」となっていますが、1つ目は「(A)のみ成立」、2つ目は「(A)(B)とも成立」、3つ目は「1つも成立していない」で、「(B)のみ成立」のパターンが抜けています。そのようなパターン（"5000"とか"4888"とか）も試してみましょう。

paiza.ioでのチェックが済んだら、AtCoderに提出してみましょう。
ACになりましたでしょうか？

質問等ありましたら、コメント欄にお願いいたします。