OmniAICreator/Qiita-1.07M huggingface dataset:
QJsonDocumentとQJsonObjectを使って、JSON形式で読み書きする方法

# はじめに

自作アプリの設定を、JSON形式で読み書きしたいと思い、その方法を調べたのでまとめます。


# JSON形式で保存するまでの流れ

0. QJsonObjectのインスタンスを作成

    ```cpp
    QJsonObject jsonObj;
    ```

0. 1で作成したインスタンスにデータを記録

    ```cpp
    // インスタンス[キー] = 値;
    jsonObj["name"] = m_userName;
    ```
    配列を記録したいときは、QJsonArrayのインスタンスを作成し、それを代入します。

    ```cpp
    QJsonArray jsonArr;

    for (auto name : m_nameList)
    {
        jsonArr.append(name);
    }

    jsonObj["nameList"] = jsonArr;
    ```

0. QJsonObjectから、QJsonDocumentインスタンスを作成

    ```cpp
    QJsonDocument jsonDoc(jsonObj);
    ```

0. QJsonDocumentインスタンスからQByteArrayを取得

    ```cpp
    // JSON形式
    QByteArray data(jsonDoc.toJson());
    ```
    バイナリ形式で書き出す場合はtoBinaryData()を使います

    ```cpp
    // バイナリ形式
    QByteArray data(jsonDoc.toBinaryData());
    ```

0. ファイルオブジェクトに書き込む

    ```cpp
    QFile saveFile(filename);
    saveFile.open(QIODevice::WriteOnly);
    saveFile.write(data);
    saveFile.close();
    ```

# JSON形式のデータを読み込むまでの流れ

0. データをバイト列として読み込む

    ```cpp
    QFile openFile(QIODevice::ReadOnly);
    QByteArray data = openFile.readAll();
    ```

0. 読み込んだデータから、QJsonDocumentを作成する

    ```cpp
    // JSON形式で書き出されたファイルを読み込む時
    QJsonDocument jsonDoc(QJsonDocument::fromJson(data));
    ```

    バイナリ形式で書き出されたファイルを読む場合は、fromBinaryDataを使います

    ```cpp
    // バイナリ形式で書き出されたファイルを読み込む時
    QJsonDocument jsonDoc(QJsonDocument::fromBinaryData(data));
    ```
    
0. QJsonDocument::object()を使って、QJsonObjectを取得する

    ```cpp
    QJsonObject jsonObj(jsonDoc.object());
    ```

0. QJsonObjectから値を読みだす

    読み出した値は、適切な型に変換する必要があります

   ```cpp
   m_name = jsonObj["name"].toString();

   QJsonArray jsonArr = jsonObj["nameList"];
   for (auto filePath : jsonArr)
   {
        filePathList << filePath.toString();
   }
   ```

詳しい使い方や実例は、公式サイトにものっているので参照してください。
[Qt Documentation - JSON Save Game Example](http://doc.qt.io/qt-5/qtcore-json-savegame-example.html)
上記サイトでは、データを保持するクラスに、QJsonObjectにデータを読み書きするためのメンバ関数、read(QJsonObject &json)、write(const QJsonObject &json)をもたせています。

# サンプル

JSON形式でファイルを読み書きするサンプルプログラムを、GitHubに上げておきました。
ただの読み書きでは面白くないとおもい、簡単なスライドショーアプリを作ってみたのですが、かえってコードが見づらくなったような気がします。  
読み書きしている部分は、MainWindowクラスのopen()とsave()、それからPlaylistクラスとSlideshowSettingクラスのreadFromJson（）とwriteToJson（）です。

[GitHub - SimpleSlideShow](https://github.com/tatsuteb/SimpleSlideShow)


#おわりに

今回は、単純なデータをJSON形式でサクッと書き出してみました。
今後は、圧縮した画像も一緒に保存する、なんてこともやりたいです。
AWS Athena で JSON ファイルを取り扱ってみたまとめ


AWS Athena は AWS 上のリソースを Database のように扱えるサービスです。 

主な用途としてはログファイルの解析とかになるかと思いますが、

S3 上に JSON ファイルをボスボス配置して 簡易 CMS 的な使い方もできたりします。

## データの準備

まずは S3 のバケットを作成します。

Athena のリージョンと S3 のリージョンはあわせたほうがいいんでしょうか…?

作成したバケットの中にフォルダを作成し、中に JSON ファイルを配置します。

JSON ファイルは １ファイルが１レコードという扱いになるので、`{` から書き始める形になります。ファイル名は無視されます。

以下のような形式の JSON ファイルはNGです。

```
{
  "title":"hgoe",
  "url": "piyo"
}
```

必ず以下のような形でアップロードします。

```
{"title":"hoge","url": "piyo"}
```

以下のように意図しない空行が末尾にあるとnullレコードが出来たりします。

```
{"title":"hoge","url": "piyo"}


```

位置ファイル内に複数レコード必要な際には、以下のように記述します。

````
{ ... },
{ ... }
````

ファイル名は日本語でもOKです。

中にフォルダを作って深い階層においてもOK

データ内に日本語が入っていてもOKです。

## テーブルの作成

Athena の管理コンソールの`add table`からテーブルを作成します。

https://console.aws.amazon.com/athena/home

テーブルの作成時のLocationには`s3://bucket/folder/`の形式でフォルダを選択します。

指定されたフォルダの中のデータ全てが読み取り対象となり、異常なオブジェクトが1つでもあるとクエリを実行出来ません。

無精して手作業でオブジェクトを運用とかはちょっと無理っぽい気がします。`gulp-yaml`とかを使用してJSONファイルを自動生成するのをおすすめします。

## クエリの発行

テーブルを作成するとクエリを発行出来ます。 

列に指定したプロパティが存在しない場合 `null`で扱われます。

int 型は `3` でも `"3"` でも正常に認識されますが、 `3hoge`のように文字列を混入させると、 **クエリの発行自体ができなくなります。**

タイムスタンプは UnixTimestamp を使用するようです。

ダッシュボードのバグなのか何なのか知らないですが、オブジェクトを追加削除した瞬間のクエリ結果は一瞬おかしくなります。

現場からは以上です。
Windows版vCenterにログインできなくなった際の作業メモ

#概要
再度一から調査すると時間が掛かるので、
遭遇したvCenterにログインできない事象に対して、調査・対応を行った際のメモを記載する。

VMwareのトラブルシューティングのKBを参照・サポートへの問い合わせを行い、切り分けしていくのが正規の手順です。
以下の内容はメモになりますので、正確性に欠ける部分があります。
同様の事象でも原因は異なる場合があることをご了承ください。
メモなので詳細情報は割愛します。

#環境
OS:
-WindowsServer2008R2
-非ドメイン環境
SW:
-vCenterServer5.1
-ESXi5.1
-Microsoft SQL Server 2008 Express
-Microsoft SQL Server 2008 R2 RTM - Management Studio Express

#確認した事象#
1.vCenterサービスが停止状態である
2.vCenterサービスを手動起動させるとエラーメッセージが出力され、サービスは起動しない
3.直近でvCenterに関連する作業は実施していない
4.ESXi単体にはvSphereClientでログインできる
5.WindowsOSの再起動でも自動起動しない

#調査方法
VMwareのトラブルシューティング関連のKB
インターネット上の技術系ブログ
WindowsOSのイベントビューアのログ

#原因と対応メモ(3件)
##1.vCenterDBの容量肥大の影響
**事前準備**
・Microsoft SQL Server 2008 R2 RTM - Management Studio Expressのインストール

**対応内容**
vCenterの起動に必要な空き容量が不足していることを確認した。
Microsoft SQL Server 2008 R2 RTM - Management Studio Expressを用いて該当DBの容量を圧縮したところ
正常にvCenterサービスが起動し、ログインに成功した。

・作業手順は以下のKBを参照した。図も掲載されているのでわかりやすい。
*Microsoft SQL DBサーバ上に「データベース’VIM_VCDB'用のトランザクション ログがフルになっています」エラーが発生する (1038150)*

**コメント**
SQL文を書ける場合は作業前にDB容量を確認してことが望ましい。
EXPRESS版のDBを使い続ける限り、定期的に発生する事象と思われる。

##バンドルされたMicrosoft SQL Server 2008 Expressのポート番号の影響
**事前準備**
特になし
**対応内容**
vCenter Single Sign-Onの設定ファイル記載のSSO用のSQLServerのポート番号と
実際のSQLServerのSSO用ポート番号に差異があった。
設定ファイル内のSSO用のSQLServerのポート番号を正規のものに書き換えたところ、正常にvCenterサービスが起動し、ログインに成功した。

・作業手順は以下のKBを参照した
*Windows ホスト マシンの再起動後、VMware vCenter Server 5.1.x Single Sign On が失敗する (2080560)*

**コメント**
前々日にWindowUpdateとOS再起動を実施したので、この時に動的にポート番号が変化したと考えられる。
詳細は不明。

##WindowsOSのログインパスワードの変更
**事前準備**
特になし
**対応内容**
OSのAdministratorのパスワードを変更して、OS再起動をしたところ、vCenterサービスが起動しなくなった。
パスワードを変更前に戻せば起動する。

<サービス>→<ログオン>内にアカウント名とパスワードを入力する欄があります。
こちらも変更後のパスワードに変更すると正常にvCenterサービスが起動し、ログインに成功した。

**コメント**
ドメイン環境下の場合はまた違ったことになったかもしれない。

#最後に
ESXiにログインできないわけではないので、すぐ影響が出てくるものではないが、
vCenterにサードパーティ製のプラグインを追加している場合は影響が出るので、早めの対処を。

以上。
python組み込み関数のお勉強（１）

# 使わないと忘れる
だいぶ前に教則本的な本を１冊通したものの、普段pythonを触らないので、割と初歩的な部分でも疎いことに気づいた。

ということで、以下、忘れないようにメモ。
今回は組み込み関数が対象。順次追加予定。

## zip関数

複数のシーケンスを同時にループできるらしい（シーケンスがよくわからないが、List等のデータのまとまりと考えればいいのか？）。

`list1 = [1,2,3,4,5]`
`list2 = [5,6,7,8,9]`
`for i, j in zip(list1, list2):`
`    print(i, j)`

結果はこんな感じ。

`1 5`
`2 6`
`3 7`
`4 8`
`5 9`

これは便利。


## sum関数
その名の通り、要素を足しあげる関数。

`list = [1,2,3,4,5]
sum(list)`

当然、結果は
`15`

この関数の面白いところは、二重リストをフラット化できること。

`list = [[1,2], [3], [4,5]]`
`sum(list, [])`

結果はこんな感じ。

`[1, 2, 3, 4, 5]`

すごい便利。

ただ、処理速度は速くないとのこと。
公式では、文字列をくっつける時はjoin関数を推奨している。

## join関数

その名の通り、文字列をjoinする。

sep.join(seq)
sepを区切り文字として、seqを連結してひとつの文字列にする。

`hiru = u'昼飯は'`
`meshi = u'カップラーメン'`
`u'、'.join([hiru, meshi])`

`'昼飯は、カップラーメン'`



上記３つの関数を組み合わせて、こんなことも可能。

`list1 = u'あまてめと'`
`list2 = u'けしおでう'`
`"".join(sum(zip(list1, list2), ()))`

２つの文字列を１文字ずつ交互に結合。

`'あけましておめでとう'`

## set（セット） ※2016/1/3 追記
setは集合を表すデータ型。
集合とは、リストとかと同様、データの集まりだが、それらと違う点は以下の2点。
**1.重複は削除される**
**2.順番がない**

特に2.がひっかかる。
え、順番がないって何？出力するときは必ず順番つくんじゃ？
って感じでイメージが湧かない。。。

とりあえず使ってみよう。
setをセット。

```
sample1 = set([1,2,3,4,5])
```

出力してみる。

```
sample1
Out[3]: 
{1, 2, 3, 4, 5}
```

やっぱ順番あるよね。。。
とりあえず順番についてはスルー。

setの便利なところは、集合というだけあって集合演算ができるらしい。
ということで、集合をもう一つ準備。

```
sample2 = set([1,3,5,7,9])
```

和集合

```
sample1 | sample2
```

```
Out[5]: 
{1, 2, 3, 4, 5, 7, 9}
```

差集合

```
sample1 - sample2
```

```
Out[6]: 
{2, 4}
```

```
sample2 - sample1
```

```
Out[7]: 
{7, 9}
```


積集合

```
sample1 & sample2
```

```
Out[8]: 
{1, 3, 5}
```

「順番がない」ということの意味や、知っとかないとつまずくところなどはよくわからん。
当分は知らなくても良さそう？良いことはないんだろうけど。



# 悩み
「なんかもっと良くならないかなぁ」という課題を、忘れないようにメモ。

## 複数の文字パターンを一発で削除

"Now I need a drink, alcoholic of course, after the heavy lectures involving quantum mechanics."という文を単語に分解し，各単語の（アルファベットの）文字数を先頭から出現順に並べたリストを作成せよ．

というやつ（よく見るから有名？）。

以下のようにやってみたのだが、
`str = "Now I need a drink, alcoholic of course, after the heavy lectures involving quantum mechanics."
print([len(i.replace(',', '').replace('.', '')) for i in str.split()])
[3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5, 8, 9, 7, 9]`

この部分
`i.replace(',', '').replace('.', '')`
が冗長。どうにかならんものか。


2016/1/2 追記
ググったらtranslate関数を使って
`str.translate(None, ',.')`
なることができるとあったが、出来なかった（2.x系と3.x系の違い？）
IntelliJをターミナルから起動する

# idea

```bash
$ idea ./
```

ディレクトリを指定するだけで起動完了

## エラー発生したら

```bash
No IDE instance has been found. New one will be started.
```

自動でIntelliJが起動されるので待ってください。
起動しない場合は手動でIntelliJを起動して、再度コマンドを実行してください。
PHPstormをターミナルから起動する

# pstorm

```bash
$ pstorm ./
```

ディレクトリを指定するだけで起動完了

## エラー発生したら

```bash
No IDE instance has been found. New one will be started.
```

自動でPHPStormが起動されるので待ってください。
起動しない場合は手動でPHPstormを起動して、再度コマンドを実行してください。
PHPのimplode関数をJavaで実装

## 概要
PHPのimplode関数のようなものをJavaで実装しました。

（追記） Java8には[join](https://docs.oracle.com/javase/jp/8/docs/api/java/lang/String.html#join-java.lang.CharSequence-java.lang.Iterable-)という関数があるそうです。
@nishemon さんコメントありがとうございます！

## 実装

```java
/**
 * Join list elements with a string
 *
 * @param stringList The list of strings to implode.
 * @param glue The String for joining list.
 * @return Returns a string containing a string representation of all the list elements
 *          in the same order, with the glue string between each element.
 */
public static String implode(List<String> stringList, String glue) {
    StringBuilder stringBuilder = new StringBuilder();
    int index = 0;
    int size = stringList.size();

    for (String value : stringList) {
        stringBuilder.append(value);

        if (index < size - 1) {
            stringBuilder.append(glue);
        }

        index++;
    }

    return stringBuilder.toString();
}
```


（追記）汎用的な実装を教えていただきました。
@shiracamus さんコメントありがとうございます！

```java
public static String implode(Iterable<? extends CharSequence> values, CharSequence glue) {
    StringBuilder buffer = new StringBuilder();
    CharSequence separator = "";
    for (CharSequence value : values) {
        buffer.append(separator).append(value);
        separator = glue;
    }
    return buffer.toString();
}
```


（追記）またまた実装を教えていただきました。
@saka1029 さんコメントありがとうございます！

```java
public static <T> String implode(List<T> list, String glue) {
    StringBuilder sb = new StringBuilder();
    for (T e : list) {
        sb.append(glue).append(e);
    }
    return sb.substring(glue.length());
}
```

## テスト

とりあえず簡単なのを一個だけ

```java
@Test
public void testImplode() {
    ArrayList<String> list = new ArrayList<>();
    list.add("A");
    list.add("B");
    list.add("C");

    String glue = " ";
    String actual = Util.implode(list, glue);

    String expected = "A B C";
    assertEquals(expected, actual);
}
```

## PHPの`implode()`について
PHPの[マニュアル](http://php.net/manual/ja/function.implode.php)を見ると、以下のように書いてあります。

> 注意:
implode()は、歴史的な理由により、引数をどちら の順番でも受けつけることが可能です。しかし、 explode() との統一性の観点からは、 ドキュメントに記述された引数の順番を使用する方が混乱が少なくなるでしょう。

また、PHPだと`glue`のデフォルトは空文字列なのですが今回は考慮していません。
やるとしたらこんな感じにオーバーロードしたものを作るのもいいかもしれません。

```java
public static String implode(List<String> stringList) {
    return implode(stringList, "");
}
```

## 補足
間違っているところやもっといいやり方あったら教えてください！ :pray: 

## 参考
- [PHP: implode - Manual]
(http://php.net/manual/ja/function.implode.php)
Tips: 「⌘英かな.app」は英語を含むようにリネームすると Spotlight から検索できるのでちょっと役に立つ

めっちゃ些細な Tips です。 (タイトルですべてを語っています。)

私は macOS を非 JIS 配列のキーボードで使っているときには、 IME の切り替えに [⌘英かな](https://ei-kana.appspot.com/) を使っています。

以前は [Karabiner](https://pqrs.org/osx/karabiner/) を使っていましたが、 Sierra へのアップデート後から Karabiner が動作しなくなったので乗り換えたくちです。

# 突然の死

「⌘英かな」は、ごくたまに突然動作しなくなることがあります。 (体感的には 1 週間に 1 回くらい)
原因を特定できたら報告したいところですが、いまのところわかっていません。

クラッシュしてしまうと Command キー単体で入力しても、 IME の切り替えが起こりません。
そういうときは、まぁ、一旦終了してから再起動しています。

# Spotlight で検索できない

ところが、終了させたあとまた起動しようにも IME が英語になってしまっていて、
日本語が入力できない状態になってしまってので Spotlight から「⌘英かな」で検索することができません。

Spotlight にかぎらず、この手の検索するタイプのランチャーでは起動できないでしょう。

しかたなく、毎度 Finder で Applications フォルダを開いたり、 Launchpad から探して起動していました。キーボードフリークには耐えられないでしょう。

# アプリケーション名に英語を足せばいい

じゃあどうすればいいか、といえば単純で、英語がないなら英語を足せばいいじゃない、というのが解です。

私は `⌘英かな (command-ei-kana).app` にリネームしました。

<img width="130" alt="⌘英かな (command-ei-kana).app" src="https://qiita-image-store.s3.amazonaws.com/0/25886/2d02cb3d-3ec8-008d-4048-10d5a10da101.png">

これで Spotlight からでも検索できるようになりました。 `kana` で検索できています。
やったね、ちゃんちゃん。

![Screen Shot 2017-01-02 at 16.55.58.png](https://qiita-image-store.s3.amazonaws.com/0/25886/307cab0d-9e64-4e49-32b5-37ed8dcee0bb.png)
スライサー（FDM式３Ｄプリンタ向け）の作成　其の４（法線）

* [スライサー（FDM式３Ｄプリンタ向け）の作成　目次](http://qiita.com/isTwt/items/5d40286eec73296ea790)

-----

# １．はじめに
　モデルデータは、頂点で囲まれた面で構成されたものになります。この面には法線というものがあり、表の方向を示すベクトルになります。
　スライサーでは、この法線情報から当該面が区切る壁としてどちらの方向が内側か（外側か）を判断することになります。

# ２．面を構成する頂点と法線の関係
　面は最低３頂点で面積を持ち法線が定義できます。ＳＴＬファイルでは、３頂点で面を構成します。
　ので、まず頂点の並びと法線の関係を定義します。（ＳＴＬファイル内の定義と一致するはず）

　下図で、Ｐ１，Ｐ２，Ｐ３の順で面が構成される場合、Ｚ＋方向が法線方向（図中矢印）となります。（スライサー座標軸）
　この場合の法線は　(X,Y,Z)=(0,0,1)となります。（単位ベクトル化）
![法線.png](https://qiita-image-store.s3.amazonaws.com/0/157557/816f0045-a7fa-e48a-72d5-f7645e1f3e84.png)

# ３．法線の算出式
　法線の算出はベクトルの外積を利用しました。
　ソースコードの関連部分を抜粋します。
　T_VERは構造体で、X,Y,Z値を保持する頂点を表します。

```c
	// ﾍﾞｸﾄﾙの長さ算出(3D-xyz)
	double VectorUtil::Length(T_VER v)
	{
		return sqrt(v.x * v.x + v.y * v.y + v.z * v.z);
	}

	// 2頂点からﾍﾞｸﾄﾙ算出(3D-xyz)
	T_VER VectorUtil::Vector(T_VER p0, T_VER p1)
	{
		T_VER	 v;

		v.x = p1.x - p0.x;
		v.y = p1.y - p0.y;
		v.z = p1.z - p0.z;

		return v;
	}

	// ﾍﾞｸﾄﾙの正規化(3D-xyz)
	T_VER VectorUtil::Normalize(T_VER v)
	{
		double	 l;
		T_VER	 n;

		l = Length(v);
		if (l) {
			n.x = v.x / l;
			n.y = v.y / l;
			n.z = v.z / l;
		} else {
			n.x = 0;
			n.y = 0;
			n.z = 0;
		}

		return n;
	}

	// ﾍﾞｸﾄﾙの外積
	T_VER VectorUtil::CrossProduct(T_VER p0, T_VER p1, T_VER p2)
	{
		T_VER	 v[2];
		T_VER	 n;

		v[0] = Normalize(Vector(p1, p0));
		v[1] = Normalize(Vector(p2, p0));
		n.x = v[0].y * v[1].z - v[0].z * v[1].y;
		n.y = v[0].z * v[1].x - v[0].x * v[1].z;
		n.z = v[0].x * v[1].y - v[0].y * v[1].x;
		return Normalize(n);
	}
```

# ４．２次元での法線（？）
　スライスするとき、最初に３次元のモデルデータを特定のＺ位置でスライスし、あとは２次元での演算（考え）が主となります。
　このとき、ある稜線に対し、前記法線と同様の考えを導入しています。
　これは、その稜線に対しどちらが内側（外側）か？を判断するためです。

　頂点を連続的に結んでいき閉領域を定義しますが、このとき、内側がどちらなのかということを法線の概念で保持していることになります。

　下図をあるスライス面とします。
 ![法線2.png](https://qiita-image-store.s3.amazonaws.com/0/157557/9a01c085-40ca-00f2-e4b3-05b3d6a29328.png)
　P1~P4の頂点で構成され、P1~P4には順番に意味をもたせます。このとき稜線P1-P2の場合、図で下側（ベクトル進行方向の右手が外側（左手が内側））として処理します。
　演算は、稜線の頂点からベクトルを算出し、Ｚ＋軸で９０度回転させた方向を法線扱いしています。

# ５．おわりに
　法線などについては、ググるとでてきます。大丈夫だと思いますが誤りなどがあれば教えてください。
mbstring.func_overloadを有効にしたときのリフレクション情報を確認する

PHPのリフレクション機能といえば大昔から真面目に実装されている割にはドキュメントが一切ないことで有名です（例：[ReflectionFunctionAbstract::getExtensionName()](http://php.net/manual/ja/reflectionfunctionabstract.getextensionname.php)）。見りゃわかるでしょ的な機能も多いんですが、とはいえ久々に見るとウッとなるので皆さん少しずつでもメモを残せばいいと思います。


# 拡張モジュール名と関数名を取り出す

さて、早速ですが`mail()`関数と`strlen()`関数の拡張モジュール名と関数名を取り出してみましょう。

```php:reflection-test.php
<?php
$refl_methods = [
    'getExtensionName',
    'getName',
];
$target_func =[
    'mail',
    'strlen',
];
foreach ($target_func as $func) {
    $refl = new \ReflectionFunction($func);
    $ret = [];
    foreach ($refl_methods as $method) {
        $ret[$method] = $refl->$method();
    }
    var_dump($ret);
}
```

これを実行すると以下の結果を得ます。

```
$ php /tmp/reflection-test.php
array(2) {
  ["getExtensionName"]=>
  string(8) "standard"
  ["getName"]=>
  string(4) "mail"
}
array(2) {
  ["getExtensionName"]=>
  string(4) "Core"
  ["getName"]=>
  string(6) "strlen"
}
```

最初の配列から、`mail()`関数はstandard拡張モジュールに属していることがわかります。つまり、`mail()`の実装を調べたかったらPHPソースコードの`ext/standard/`以下を探せばいいわけです（普通はそんなことせずに全体を`grep`すると思いますが）。

一方、`strlen()`の拡張モジュール名は「Core」だそうです。そういえば`phpinfo()`にもCoreって書いてありますけど、今まで気にしたことがありませんでしたね。他の拡張モジュールと異なり、この実体は`Zend/zend_builtin_functions.c`にあります。

# `mbstring.func_overload`を有効にしてみる

さて、上のコードを`mbstring.func_overload`を有効にして再度実行してみましょう。`mbstring.func_overload`はPHPの一部の組み込み関数をmbstringの提供する関数に置き換えてしまうというPHPのオシャレ機能で、[PHP 7.2で非推奨に格下げにしようかどうか議論をしている](https://wiki.php.net/rfc/deprecations_php_7_2)というステータスです。

```
$ php -dmbstring.func_overload=3 /tmp/reflection-test.php
array(2) {
  ["getExtensionName"]=>
  string(8) "mbstring"
  ["getName"]=>
  string(12) "mb_send_mail"
}
array(2) {
  ["getExtensionName"]=>
  string(8) "mbstring"
  ["getName"]=>
  string(9) "mb_strlen"
}
```

`mbstring.func_overload`で関数が置き換えられた結果、どちらの関数もmbstring拡張モジュールに所属していることがわかります。また、`getName()`メソッドの返す値は実体の関数名`mb_***()`になっています。少し面白いですね。
Webpack2のパフォーマンス警告を制御する


備忘録

webpack2で下記のような警告が出る

```
WARNING in asset size limit: The following asset(s) exceed the recommended size limit (250 kB).
This can impact web performance.
Assets:
  my-file.min.js (251 kB)

WARNING in entrypoint size limit: The following entrypoint(s) combined asset size exceeds the recommended limit (250 kB). This can impact web performance.
Entrypoints:
  main (251 kB)
      my-file.min.js


WARNING in webpack performance recommendations:
You can limit the size of your bundles by using import() or require.ensure to lazy load some parts of your application.
For more info visit https://webpack.js.org/guides/code-splitting/
```

警告は直せるほうが良いとはいえ、デフォルト設定がかなりきつく（多分require.ensureとかSystem.importをベースに考えられている）
真正面から向き合おうとするとなかなか簡易じゃないパターンがあったり、ライブラリビルドの場合そもそも無用なものだったりするパターンがある。

# 解決編

ざっくりオフにしてしまうなら下記

```js
module.exports = {
  module: {
   //...
  },
  plugins: [
   //...
  ],
  output: {
   //...
  },
  // ...
  performance: { hints: false } // これ
}
```

詳しくは下記参照

https://webpack.js.org/configuration/performance/#performance-hints

全部オフにせず閾値を変えるのも出来る

* maxEntrypointSize
    * entrypointサイズの警告の閾値を変更する。
    * defaultは250kb
* maxAssetSize
    * assetのファイルサイズ警告の閾値を変更する
    * defaultは250kb
* assetFilter
    * asset警告を出すファイルを決定する関数
    * `.map`ファイルは無視するとか出来る
【Max/MSP】function オブジェクトでポイント数を固定にする方法

# functionオブジェクトでポイント数を固定にする方法

Max/MSPでファンクションオブジェクトをポイントだらけにしたくない時の対処法をよく忘れてしまうのでメモ

1. functionオブジェクトを作成
2. あらかじめ必要なポイントクリックして入れておく
3. インスペクタを表示
4. Allows Adding Points by... のチェックをはずす

<img width="821" alt="スクリーンショット 2017-01-02 16.26.40.png" src="https://qiita-image-store.s3.amazonaws.com/0/147344/d64efda8-1ebf-ecac-d885-c06fd71ab433.png">
AngularJSでCheckBoxの値を外しても更新できない場合の対処法


## Webアプリ開発とCheckBoxのデータの受け渡し
Webアプリを開発する際に、画面からのデータの受け渡しは必ず発生します。
その中でも特に、CheckBoxのデータの受け渡しで結構頭を悩ます方も多いのではないでしょうか？
多くのWebアプリ開発用のフレームワークでViewHelperなどにコンポーネントの形で実装されてることも多いと思います。

## AngluarJSでのCheckBoxのデータの受け渡し
AngularJSでも他のWebアプリ開発用のフレームワークに漏れず、コンポーネントについてサポートしています。
しかし他のフレームワークと決定的に違うのは、以下のようにCheckBoxを外した場合の値についても定義できる点です。

```
<input type="checkbox" ng-model="checkboxModel" ng-true-value="'YES'" ng-false-value="'NO'">
```

上記はチェックを付けた場合には「YES」、外した場合には「NO」という値を送信する例です。
今までバリデーションチェックなどの処理で苦労していましたが、これで余分な処理を実装しなくて済みそうですね。


## 参考
* [input【checkbox】(AngularJS公式ドキュメント)](https://docs.angularjs.org/api/ng/input/input%5Bcheckbox%5D)
スライサー（FDM式３Ｄプリンタ向け）の作成　其の３（座標軸）

* [スライサー（FDM式３Ｄプリンタ向け）の作成　目次](http://qiita.com/isTwt/items/5d40286eec73296ea790)

-----

# １．はじめに
　３Ｄプリンタ，スライサー，モデリングソフトなど、ソフトや、ハードにはそれぞれの座標軸が存在します。
　現状スライサーは、私の３Ｄプリンタと同じ座標軸で実装していますが、モデリングソフトであるShade3Dは別座標軸となっています。
　そのため、今回座標軸の話をしておきます。

# ２．３Ｄプリンタ（スライサー）の座標軸
![axis-slicer.JPG](https://qiita-image-store.s3.amazonaws.com/0/157557/33c3fb10-3887-82f8-3803-4c99bae589d4.jpeg)
* 水平面はＸＹ軸
* 横方向Ｘ軸（右側＋）
* 奥方向Ｙ軸（奥側＋）
* 高さ方向Ｚ軸（上側＋）

# ３．モデリングソフト（Shade3D）の座標軸
![axis-shade.JPG](https://qiita-image-store.s3.amazonaws.com/0/157557/4f82af07-ec3d-f998-dcba-e60a2789f354.jpeg)
* 水平面はＸＺ軸
* 横方向Ｘ軸（右側＋）
* 奥方向Ｚ軸（手前側＋）
* 高さ方向Ｙ軸（上側＋）

# ４．おわりに
　モデリングソフトであるShade3DからSTLファイルにエクスポートする場合、座標軸については、変換できるオプション指定が可能です。
　しかしながら、それぞれの座標軸についてはまとめておかないと混乱してしまいます。
Composerで名前空間を使う

## Composerとは

[Composer](https://getcomposer.org/)とはPHPでパッケージ管理を行う仕組みです。
PHPで外部ファイルを多数読み込む場合に、requireやincludeを多数定義する必要があります。
しかしComposerを使うと、bootstrapとなるファイルのみの読み込みで、多数のファイルを読み込むことが可能になります
そのためライブラリの使用時などにとても適しています。

## Composerのインストール
以下のコマンドでcomposer.pharをインストールします。

```
$ curl -s http://getcomposer.org/installer | php
```

## composer.json作成
composer.jsonを以下のように作成します。

```
{
    "repositories": [
        {
            "packagist": false
        }
    ],
    "autoload": {
        "psr-4": {
            "SRAUFactory\\" : "src/",
        }
    }
}
```


## パッケージのインストール
以下のコマンドを実行します。

```
$ php composer.phar install
```

「Generating autoload files」という文言とともに、以下のようにファイル生成されれば、インストール完了です。

```
composer.json
vendor/autoload.php
vendor/composer/ClassLoader.php
vendor/composer/LICENSE
vendor/composer/autoload_classmap.php
vendor/composer/autoload_namespaces.php
vendor/composer/autoload_psr4.php
vendor/composer/autoload_static.php      
vendor/composer/autoload_real.php
vendor/composer/installed.json
```

## パッケージの使用方法
###autoload.php参照
以下のようにautoload.phpを参照してください。

```
require 'vendor/autoload.php';
```

###クラスファイルの読み込み
```
// /src/Common/Util.phpの読み込み
use SRAUFactory/Common/Util;

Util::import();

// useを使わない場合
SRAUFactory/Common/Util::import();
```

## 参考
* [Composer公式サイト](https://getcomposer.org/)
* [[php][composer]composerでPHPのプロジェクトを簡単に始める](http://d.hatena.ne.jp/brtRiver/20120610/1339350390)
AnimatorのEntryに設定したTransitionの判定が行われるタイミングがわからなかったので調べてみた

Unity5.5.0f3で調べました。
Base LayerとSubStateMachineが１ずつあるという想定です。

[ Base LayerのEntryが呼ばれるタイミング ]
・SubStateMachineの (Up)　からBase Layerを指定して遷移してきたとき
・BaseLayerのExitに遷移したとき

[ SubStateMachineのEntryが呼ばれるタイミング ]
・Base LayerからSubStateMachineを指定して遷移したとき




Animator起動時や遷移先がなくなった場合などは
デフォルトのStateから直接始まるためEntryは呼ばれず、遷移判定も行われないため注意。




それぞれのEntryが呼ばれるタイミングで
Entryに設定したTransitionの判定が行われます。
また、StateMachineBehaviourのOnStateMachineEnterもそのタイミングで呼ばれます。

何か間違ってたらご指摘下さい。
書評: Ansible実践ガイド / 北山晋吾・著 / インプレス (2016.12)

最近同僚が書いた本の書評をひとつ。

> Title: Ansible実践ガイド (Impress top gear) 
> Publisher: インプレス (Dec. 21, 2016)
> Author: 北山 晋吾
> ISBN-13: 9784295000464
> Amazon: http://amzn.asia/baqt6oa

まず、感想を大きく2点ほど。
1) 単なる技術やプロダクトの入門書ではなく、ビジネスや運用を意識した上で、ansible をどう使いこなしてまさに「実践」すればよいのかを教えてくれる本。辞書として使うのは間違いで、読み進めるにしたがって自分で考えながら手を動かす必要がある。
2) ぜひ査読させてほしかったw

本書の構成は以下のようになっている。

* 1章 Ansibleの概要
* 2章 Ansibleの基礎
* 3章 プレイブックとインベントリ
* 4章 アプリケーションデプロイメント
* 5章 システムの構成管理
* 6章 ブートストラッピング
* 7章 Infrastructure as Code の実践

最初の3章までが基礎編、4章以下が具体的なテーマに即した実践編である。

内容に入る前にざっくり条件を。

* 対象バージョン: ansible 2.2
* ansible 実行環境: CentOS 7.2
* ansible の install 形態: distro package manager, pip, source install が網羅されている。
* サンプルコード(プレイブック)は以下で公開されている。筆者はまだ試せていないが、基本的に記述の通りに作業すれば問題なく動作する(と、思う)。
    * https://gitlab.com/shkitayama/ansible_practical_guide/

以下、各章の紹介に移る。

1章では、Business Agility からはじめて、"クラウド" "DevOps" と話をつなげる中で、構成管理の変遷にともない、なぜ ansible のようなものが必要になったのか、説いている。
クラウド登場以前までの「ITサービスとしての構成管理」は、考え方としては ITIL ・ツールとしてはCMDBで行われてきた。これは、ある意味静的な構成管理であった。一方、クラウド以後に必要性が顕在化してきたのは 「動作しているシステムの(ある意味動的な)構成管理」である。これは、筆者の言葉を借りれば、「システムをあるべき状態に収束させること」とも言える。

この際、Infrastructure as Code といった「しくみ」を適用しようとするだけでなく、「しくみ」自体を組織の実情にあった形で展開するだとか、業務・運用の手順、さらには組織の文化を**継続的に改善**していくことが重要である。
これがもっとも重要な論点であり、実際本書を通して繰り返し述べられている。

2章と3章が ansible の基本的な解説である。

4章以下が、具体的なシナリオと playbook 例に基づいたansible の実践方法の解説である。

* 4章 アプリケーションデプロイメント

keepalived + HAProxy + Apache2 + MySQL という多層クラスタ構成のWordpressサービスが題材である。単純に初期デプロイを行うだけでなく、台数増減やローリングアップデートのような運用シナリオも含め、具体的な playbook 例に基づいて ansible の使いこなし方が解説されている。

これは、5章以降でも言えることだが、現実的に維持可能な運用のためには、何に気をつけるべきなのか？繰り返し強調される。しかも、どんな組織にでも適用可能な絶対の答はないので、自分で考え続けることが重要である。

* 5章 システムの構成管理

LinuxとWindowsを題材にとり、OSの初期設定 ansible で構成する方法が具体的に解説されている。
筆者には、特に、Windows でここまで自動化が可能になっているのは新鮮だった。

* 6章 ブートストラッピング

6章の題材は、インフラレイヤのリソースプロビジョニングである。
API経由でインフラが操作できるクラウド環境として、Docker と OpenStackを題材に、ansible を用いてクラウド基盤上にインフラリソースを作成する方法が解説されている。
本章のキーワードとしては**ダイナミック・インベントリ** の考え方だろうか。

なお、ベアメタルへのOSプロビジョニングも、他のツールと組み合わせて ansible で制御はできるのだが、本書では割愛されている。[^1]  
[^1]: 昨今は、Composable Infrastructure 等と、物理的なハコもAPI管理できるようになりつつあるが、それはまた別の話。
余談だが、AWSやAzure等のPublic Cloudを例にとってもよかったのではないかと思う。ネット上や類書で情報が豊富にある(だろう)ことと、紙面の問題だろうか。


* 7章 Infrastructure as Code の実践
 
最後の7章は、6章までの具体的なシナリオに即した解説にはそぐわない、全体的なベストプラクティスがまとめられている。

前半は「プレイブックのベストプラクティス」で、管理対象の規模に応じたプレイブックの構成方法（特に、柔軟性と可読性・保守性のトレードオフ）と**再利用**の実例、パフォーマンス・チューニング、トラブルシューティングである。
後半では、ansible そのものから一歩踏み出して、プレイブックのコーディング規約、バージョン管理、(プレイブック自体の)CIがカバーされている。

* そのほか

全体的な感想をもう少し。
個人的には、**「レビュー」**の観点をもう少し入れても良かったのではないかと思う。筆者がかかわっている界隈では github の PR 機能ではなく gerrit を使っているのだが、これも紙面の都合だったのかもしれない。

* まとめ

以上、単純なツールの使い方の解説ではなく、現場でどう使いこなして**実践**すればよいのか、具体的な例を交えて詳細に解説されている本である。オススメの一冊ではあるのだが、読者にもいろいろ要求する本なので、心して読んでほしい(笑)

* Disclosure

本書の著者は職場の同僚ですが、私は自費で本書を購入しました。
boost::shared_ptr から std::shared_ptr へ変換する簡単な方法

# 方法

```cpp
// std::shared_ptr
#include <memory>
// boost::shared_ptr
#include <boost/shared_ptr.hpp>

auto main() -> int
{
  boost::shared_ptr< int > b = boost::shared_ptr<int>( new int( 123 ) );
  std::shared_ptr< int > s = std::shared_ptr<int>( x.get(), [x] ( ... ) mutable { } );
}
```

# 検証

## 挙動の確認

「方法」の比較的簡潔なコードに、挙動の確認に適当なブロックスコープと `std::cout` などを仕込む例を紹介。

```cpp
#include <iostream>
#include <memory>
#include <boost/shared_ptr.hpp>

using namespace std;

int main()
{
  std::cout << "scope-A{\n";
  {
    std::cout << "scope-B{\n";
    std::shared_ptr< int > s;
    std::cout << "s = " << s << '\n';
    {
      std::cout << "scope-C{\n";
      boost::shared_ptr< int > b = boost::shared_ptr< int >( new int( 123 ) );
      std::cout << "b = " << b << '\n';
      // 今回は解説の都合 b でキャプチャーすると紛らわしいので bc としてコピーキャプチャーする例示にします。
      s = std::shared_ptr<int>( b.get(), [ bc = b ] ( ... ) mutable { std::cout << "reset bc in dtor lambda of s\n"; } );
      std::cout << "s = " << s << '\n';
      std::cout << "}scope-C\n";
    }
    std::cout << "s = " << s << '\n';
    std::cout << "}scope-B\n";
  }
  std::cout << "}scope-A\n";
}
```

↑これをビルドして実行すると、↓こうなる。

```
scope-A{
scope-B{
s = 0
scope-C{
b = 0x1c595b0
s = 0x1c595b0
}scope-C
s = 0x1c595b0
}scope-B
reset bc in dtor lambda of s
}scope-A
```

1. `scope-A{`: `main` 関数の関数スコープの始まり。
2. `scope-B{`: `std::shared_ptr< int > s` が宣言されるブロックスコープの始まり。
3. `scope-C{`: `boost::shared_ptr< int > b` が宣言、定義され、 `scope-B` の `s` に対して「変換」が行われるブロックスコープの始まり。
4. `}scope-C`: オブジェクト `b` がスコープを外れ破棄されるタイミング。但し、「変換」が成功していれば `b` は `s` のカスタムデリーターのラムダ式に `bc` としてコピーキャプチャーされているため、 `b` が破棄されても `bc` は `s` のスコープで生存する「はず」というタイミング。
5. `}scope-B`: 「変換」が成功していれば `s` は `scope-B` の `b` と同じオブジェクトをこの時点までは間接参照できる「はず」の最後のタイミング。ここを超えるとオブジェクト `s` もスコープにより破棄されるので、 `s` のカスタムデリーターに仕込んだ `bc` の破棄出力が得られる「はず」のタイミング。
6. `}scope-A`: ↑の(5)とこの(6)の間に `s` のカスタムデリーターによる `bc` の破棄出力が得られている「はず」のタイミング。

と、いうわけで、外部から観測する挙動としては意図通りに「変換」できている事がわかる。
CircleCIでのnodeで Module Not Foundが出たときの対処法

## tl;dr
パスの指定はちゃんとしましょう。

## 問題
プロジェクトのテストをCircleCIで回していて、手元では動くテストがCircleCI上だと以下のようなエラーが出てしまっていました。


### npm test
```
[10:48:53] Using gulpfile ~/porject/gulpfile.js
[10:48:53] Starting 'test'...
[10:48:59] 'test' errored after 5.7 s
[10:48:59] Error in plugin 'gulp-mocha'
Message:
    Cannot find module 'path/to/module/Hogehoge.js'
Details:
    code: MODULE_NOT_FOUND
Stack:
Error: Cannot find module 'path/to/module/Hogehoge.js'
```

## 解決法
requireで指定していたパスのファイル名の先頭が大文字になっていてファイルと違っていました....orz
ファイル名を実態を合わせて指定したら動きました。

## 理由
OSのファイルシステムに依存するようです。macとCircleCI上のOSで挙動が違っていたみたいです。
参考：http://stackoverflow.com/questions/13617863/can-i-force-node-js-require-to-be-case-sensitive

あんまりないかもしれませんが、macとlinux系のOS両方で開発していると起こるかもしれないですね。
rex0220 KANAかなプラグイン

漢字入力時、かな項目を自動入力してくれます。

- 複数の漢字かな項目ペアを指定可能
- サブテーブル内の項目も複数指定可能
- ひらがな・カタカナの指定可能
- アルファベットをそのまま複写
- 数字をそのまま複写
- 一覧編集画面に対応
- スマホ対応

※コピペ、オートコンプリートには対応していません。
スマホでオートコンプリートが使われる場合、あまり実用的ではありません。

[rex0220 stores で、販売中です。](https://rex0220.stores.jp/)

Ver.3 変更点
・プラグイン設定で、運用環境に反映する機能追加
・プラグイン設定で、コメント欄追加
・プラグイン設定のダウンロード＆アップロード機能追加
・プラグイン設定のグリッドライブラリ変更

![2017-01-02_14h17_45.gif](https://qiita-image-store.s3.amazonaws.com/0/100572/381fbfed-ce38-d422-e6f1-9c2cc46fe44f.gif)



# 編集画面

![2017-01-02_12h49_27.png](https://qiita-image-store.s3.amazonaws.com/0/100572/35c5de54-cbd7-58ca-0ed3-879c1719e73e.png)


# 一覧編集画面
![2017-01-02_13h01_32.png](https://qiita-image-store.s3.amazonaws.com/0/100572/e9371df9-dea3-1c0b-a3d6-7e060f8fc670.png)


# スマホ編集画面

![スマホ1.png](https://qiita-image-store.s3.amazonaws.com/0/100572/5b6bee77-146e-4438-5f31-f8158d8d43df.png)


# プラグインの追加

- 「kintone システム管理 > プラグイン」で追加します。
- 「アプリの設定 > プラグイン」で、アプリに追加します。


# プラグインの設定
対象アプリで使用する機能を選択して、「保存する」をクリックします。

- プラグイン設定画面において、漢字項目とかな・カナ項目２個１組で指定します。
- 漢字項目、かな・カナ項目の入力エリアをクリックすると、テキスト項目が一覧表示されますので選択します。
- カタカナ: カタカナ変換
- 英字：　英字をかな・カナ項目に複写
- 数字：　数字をかな・カナ項目に複写
- スマホ：　スマホでKANAかなプラグイン動作

※フォーム変更時は、本番環境にフォーム変更を反映後に、本プラグイン設定を行ってください。

![2017-01-02_15h33_28.png](https://qiita-image-store.s3.amazonaws.com/0/100572/3a5217ff-7399-ed8c-6a47-bce9c81e159b.png)



# 注意事項
- 既に、JavaScript によるカスタマイズを行っているアプリの場合、処理が競合して、エラーになる場合があります。その場合は、該当するアプリでプラグインの使用を中止してください。
[JAWS-UG CLI]Amazon AppStream 2.0 入門 (7) VPC環境の削除

# この記事について

[JAWS-UG CLI専門支部 #76 AppStream 2.0入門](https://jawsug-cli.doorkeeper.jp/events/52024)で実施するハンズオン用の手順書です。


# 前提条件

## 必要な権限

作業にあたっては、以下の権限を有したIAMユーザもしくはIAMロールを利用してください。

- AppStream(2.0)のフルコントロール権限
- EC2のフルコントロール権限
- CloudFormationの関するフルコントロール権限
- IAMの関するフルコントロール権限


# 0. 準備

## 0.1. リージョンを指定

```bash:コマンド
export AWS_DEFAULT_REGION="ap-northeast-1"
```

## 0.2. 資格情報を確認

```bash:コマンド
aws configure list
```

インスタンスプロファイルを設定したEC2インスタンスでアクセスキーを設定せずに実行した場合、以下のようになります。

```text:結果
      Name                    Value             Type    Location
      ----                    -----             ----    --------
   profile                <not set>             None    None
access_key     ****************QSAA         iam-role
secret_key     ****************c1xY         iam-role
    region                us-west-2              env    AWS_DEFAULT_REGION
```

## 0.3. バージョン確認

```bash:コマンド
aws --version
```

```text:結果
aws-cli/1.11.35 Python/2.7.12 Linux/4.4.35-33.55.amzn1.x86_64 botocore/1.4.92
```

## 0.4. バージョンアップ（必要に応じて）

```bash:コマンド
sudo pip install -U awscli
```


# 1. VPC環境の削除

## 1.1. CloudFormation Stackの削除

### 変数の確認

```bash:コマンド
cat << ETX

    CF_STACK_NAME: ${CF_STACK_NAME}

ETX
```

```text:結果

    CF_STACK_NAME: VPC4AppStream20

```


### CloudFormation Stackの削除

```bash:コマンド
aws cloudformation delete-stack \
    --stack-name ${CF_STACK_NAME}
```

```text:結果
（返値無し）
```


### CloudFormation Stackの削除を待機

```bash:コマンド
aws cloudformation wait stack-delete-complete \
    --stack-name ${CF_STACK_NAME}
```

```text:結果
（返値無し）
```

### CloudFormation Stackが削除されたことを確認

```bash:コマンド
aws cloudformation describe-stacks \
    --query Stacks[?StackName==\'${CF_STACK_NAME}\']
```

```json:結果
[]
```


以上
[JAWS-UG CLI]Amazon AppStream 2.0 入門 (2) Stackの作成

# この記事について

[JAWS-UG CLI専門支部 #76 AppStream 2.0入門](https://jawsug-cli.doorkeeper.jp/events/52024)で実施するハンズオン用の手順書です。


# 前提条件

## 必要な権限

作業にあたっては、以下の権限を有したIAMユーザもしくはIAMロールを利用してください。

- AppStream(2.0)のフルコントロール権限
- EC2のフルコントロール権限
- CloudFormationの関するフルコントロール権限
- IAMの関するフルコントロール権限


# 0. 準備

## 0.1. リージョンを指定

```bash:コマンド
export AWS_DEFAULT_REGION="ap-northeast-1"
```

## 0.2. 資格情報を確認

```bash:コマンド
aws configure list
```

インスタンスプロファイルを設定したEC2インスタンスでアクセスキーを設定せずに実行した場合、以下のようになります。

```text:結果
      Name                    Value             Type    Location
      ----                    -----             ----    --------
   profile                <not set>             None    None
access_key     ****************QSAA         iam-role
secret_key     ****************c1xY         iam-role
    region                us-west-2              env    AWS_DEFAULT_REGION
```

## 0.3. バージョン確認

```bash:コマンド
aws --version
```

```text:結果
aws-cli/1.11.35 Python/2.7.12 Linux/4.4.35-33.55.amzn1.x86_64 botocore/1.4.92
```

## 0.4. バージョンアップ（必要に応じて）

```bash:コマンド
sudo pip install -U awscli
```


# 1. Stackの作成

### stackとは

Streaming resources and policies for controlling access to these resources. The streaming resources are made up of instances that are part of an AppStream 2.0 fleet.

(CloudFormationのStackとは異なります。)


## 1.1 Stackの作成

### Stack名を指定

```bash:コマンド
STACK_NAME="STACK_JAWSUG_CLI"
STACK_DESCRIPTION="A stack for test at jaws-ug"
STACK_DISPLAY_NAME=${STACK_NAME}
```


### 同名のStackが存在しないことを確認

```bash:コマンド
aws appstream describe-stacks \
    --query Stacks[?Name==\`${STACK_NAME}\`]
```

```json:結果
[]
```


### 変数の確認

```bash:コマンド
cat << ETX

    STACK_NAME: ${STACK_NAME}
    STACK_DESCRIPTION: "${STACK_DESCRIPTION}"
    STACK_DISPLAY_NAME: ${STACK_DISPLAY_NAME}

ETX
```

```text:結果

    STACK_NAME: JAWSUG_CLI
    STACK_DESCRIPTION: "A stack for test at jaws-ug"
    STACK_DISPLAY_NAME: JAWSUG_CLI

```


### Stackの作成

```bash:コマンド
aws appstream create-stack \
    --name ${STACK_NAME} \
    --description "${STACK_DESCRIPTION}" \
    --display-name ${STACK_DISPLAY_NAME}
```

```json:結果
{
    "Stack": {
        "CreatedTime": 1483115244.642,
        "DisplayName": "JAWSUG_CLI",
        "Name": "JAWSUG_CLI",
        "Arn": "arn:aws:appstream:ap-northeast-1:************:stack/JAWSUG_CLI",
        "Description": "A stack for test at jaws-ug"
    }
}
```


## 1.2. 作成したStackの確認

```bash:コマンド
aws appstream describe-stacks \
    --names ${STACK_NAME}
```

```json:結果
[
    {
        "CreatedTime": 1483329923.703,
        "DisplayName": "JAWSUG_CLI",
        "Name": "JAWSUG_CLI",
        "Arn": "arn:aws:appstream:ap-northeast-1:************:stack/JAWSUG_CLI",
        "Description": "A stack for test at jaws-ug"
    }
]
```

以上
Enum.sort または Enum.sort_by で安定ソートさせるために気をつけること

プログラミングElixir読み途中です。
引っかかりそうなところがあったのでメモしておきます。


`Enum.sort/2` の第二引数には、**同じ値の場合は `true` を返すようなを関数を渡さないと安定ソートになりません。**

```iex
iex> words = ["some","kind","of","monster"]
["some", "kind", "of", "monster"]
iex> Enum.sort words, &(String.length(&1) < String.length(&2))
["of", "kind", "some", "monster"]
iex> Enum.sort words, &(String.length(&1) <= String.length(&2))
["of", "some", "kind", "monster"]
```

`Enum.sort_by/3` でも同様です。

```iex
iex> words = ["some","kind","of","monster"]
["some", "kind", "of", "monster"]
iex> Enum.sort_by words, &String.length/1, &</2
["of", "kind", "some", "monster"]
iex> Enum.sort_by words, &String.length/1, &<=/2
["of", "some", "kind", "monster"]
```

[Enum.html#sort/2 の Example](https://hexdocs.pm/elixir/master/Enum.html#sort/2-examples) には、このことが書いていますが、sort_byの方は特に何も書いてないので… `sort`の方も見ろやってことですかね(´・ω:;.:...

[Enum.sort/2 not stable · Issue #2163 · elixir-lang/elixir](https://github.com/elixir-lang/elixir/issues/2163)のコメントにも書いてますが、自分もつい `>=` や `<=` より `>` や `<` を使うことが多いので気をつけます(｀･ω･´)ゞ
備忘録_ESlint入門_個人的メモ


完全に自分用です。

## インストール

```
$ npm install --save-dev eslint
```

## 設定ファイル

設定方法も何個があるけど、下記を使用

```
.eslintrc.json
```

設定ファイルサンプル

```
{
  "env": {
    "browser": true,
    "jquery": true
  },
  "extends": "eslint:recommended",
  "globals": {
  },
  "parserOptions": {
    "ecmaVersion": 2015
  },
  "rules": {
    "no-extra-semi": "warn",
    "no-undef": "warn",
    "quotes": ["warn", "single"],
    "space-before-blocks": ["warn", { "functions": "always" }]
  }
}
```

### env

ブラウザやjQueryなどのグローバルプロパティを一括指定

- true or false


### extends

ESLintおすすめのルールを適用させることが可能

下記参照
http://eslint.org/docs/rules/


### globals

グローバルに存在していることを明示
※基本はenvに指定。それでも対応できない場合はここで。


### parserOptions

サンプルファイルではES2015の記述に対応させるオプションを記述

詳しくは下記を参照
http://eslint.org/docs/user-guide/configuring#specifying-parser-options


### rules

もろもろルールを記述

- off / チェックしない
- warn / 警告表示
- error / エラー


## --fix オプション

`--fix`のオプションを使用することでエラー部分を自動的に書き換えてくれる
※全てを書き換えるわけでなはいので注意

下記ページを参照(スパナのマーク)
http://eslint.org/docs/rules/

```
$ eslint <対象ファイルのパス> --fix
```

## .eslintignore

除外したいファイルを記述する
※例えばjQuery自体とか・・・

```.eslintignore

/dev/lib/**

```


## -f codeframe

下記のようにオプションを追加するとエラー箇所がわかりやすくなる

```
$ eslint <対象ファイルのパス> -f codeframe
```


## neovimで使う

下記2つのプラグインを入れる

- 'neomake/neomake'
- 'benjie/neomake-local-eslint.vim'


設定ファイルに下記を追記

```
autocmd! BufWritePost * Neomake
let g:neomake_javascript_enabled_makers = ['eslint']

let g:neomake_error_sign = {'text': '>>', 'texthl': 'WarningMsg'}
let g:neomake_warning_sign = {'text': '>>',  'texthl': 'Question'}
```
Pythonのスライス

# スライス

スライスを使ってリストの要素を部分的に取得できる。

インデックス1〜3の要素を取得

```python
>>> a = [1,2,3,4,5,6,7,8,9]

>>> a[1:4]
[2, 3, 4]
```

**※ 終端は インデックス + 1の値となる**


## ステップを指定 

```python
>>> a = [1,2,3,4,5,6,7,8,9]

>>> a[1:8:2]          # インデックス1〜7の要素を2ステップで
[2, 4, 6, 8]
```

## 最後の要素にアクセス
```python
>>> a = [1,2,3,4,5,6,7,8,9]
>>> a[-1] 
9
```

-1は一番後ろの要素で、-2は後ろから2番目の要素、-3は。。。（略）

```python
>>> a[-2]
8

>>> a[-3]
7

>>> a[-4]
6
```

## スライスではインデックスをオーバーしてもエラーにならない

```python
>>> a = [1,2,3,4,5,6,7,8,9]

>>> a[5:20]
[6, 7, 8, 9]

>>> a[-100:4]
[1, 2, 3, 4]
```


## 一番最初から～○○まで
先頭を省略すると「一番最初」の要素を示す


```python
>>> a[0:4]
[1, 2, 3, 4]

```


と


```python
>>> a[:4]
[1, 2, 3, 4]
```


は同義


## ○○から～一番後ろまで
末尾を省略すると「一番最後」の要素を示す


```python
>>> a[5:len(a)]
[6, 7, 8, 9]
```


と


```python
>>> a[5:]
[6, 7, 8, 9]
```


は同義


```python
>>> a = [1,2,3,4,5,6,7,8,9]
>>> a[-4:]
[6, 7, 8, 9]
```
なんてこともできる


## すべての要素を指定


```python
>>> a[0:len(a)]
```


と


```python
>>> a[:]
```

または

```python
>>> a[::]
```

は同義

```python
>>> a = [1, 2, 3, 4, 5, 6, 7, 8, 9]

>>> a[0:len(a)]
[1, 2, 3, 4, 5, 6, 7, 8, 9]

>>> a[:]
[1, 2, 3, 4, 5, 6, 7, 8, 9]

>>> a[::]
[1, 2, 3, 4, 5, 6, 7, 8, 9]
```


## スライスされたリストは、元のリストとは別インスタンス

```python
>>> a = [1, 2, 3, 4, 5, 6, 7, 8, 9]

>>> b = a[-5:]
>>> b
[5, 6, 7, 8, 9]

>>> b[1] = 60
>>> b
[5, 60, 7, 8, 9]

# 元リストはコピーしたリストとは別インスタンスなので、変更の影響を受けない
>>> a
[1, 2, 3, 4, 5, 6, 7, 8, 9]


```

## マイナスのステップ

先にふれたようにスライスではステップが指定できた。

```python
>>> a = [1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> a[3:8:2]  # インデックス 3〜7を2ステップで
[4, 6, 8]
```

以下のようにすると逆方向にスライスできる。

```python
>>> a[7:2:-2]   # インデックス7〜3を-2ステップで
[8, 6, 4]
```


範囲を全指定にしてマイナスステップにすると、要素がリバースする。

```python
>>> a[::-1]
[9, 8, 7, 6, 5, 4, 3, 2, 1]
```

## 文字列に対して

文字列に対しても同じく以下のように。

```python
>>> txt = '123456789'

>>> txt[1:4]
'234'

>>> txt[-1]
'9'

>>> txt[:4]
'1234'

>>> txt[5:]
'6789'

>>> txt[::-1]
'987654321'
```
配列に代入演算するとnull値が入ってしまう

配列を生成したときに初期値を設定していないと
配列にnullが入ってしまった。
【コード】

```java
String[] c = new String[4];
c[1] += 3;
System.out.println(c[1]);
```

【出力結果】
null3

配列の全要素に初期値を設定するためには以下を追加したら、
nullが入らなかった。

```java
Arrays.fill(c, "");
```
情報処理技術者試験　プロジェクトマネージャー　平成27年度午後１問2

#始めに
情報処理技術者試験　プロジェクトマネージャー　平成27年度午後１問2を自分なりに問題を解析した後、IPAが公表している回答のGAP解析もしてみました

#問題の解析
![image](https://qiita-image-store.s3.amazonaws.com/0/136860/567ce982-17cc-b6d8-5b59-67ee6c7b7b51.png)
ターミナルにGitHubの草を表示する macOS

GitHubの草状況をターミナルでさっと確認できればいいなと思ってCLIツールを雑に書いた。

[akameco/github-kusa: Check the grass of GitHub at the terminal for macOS](https://github.com/akameco/github-kusa)

```
$ npm install --global github-kusa
```

[![https://gyazo.com/dc0800ba583826e89c16ef9f712de047](https://i.gyazo.com/dc0800ba583826e89c16ef9f712de047.png)](https://gyazo.com/dc0800ba583826e89c16ef9f712de047)

しかし、svg取得からのPhantomJSでpngに変換してるので表示までに5秒かかるし普通にGitHub開いた方がはやい。
フォルダ内全てのファイルをmd5のハッシュ名に名前を変更する方法

```bash
for fpath in $(find . -type f); do
  var_md5=$(md5sum $fpath | awk '{print $1}')
  var_extension=${fpath##*.}
  echo "rename $fpath to ${var_md5}.${var_extension}"
  mv $fpath ${var_md5}.${var_extension}
done
echo "rename done!"
```

参考サイト
-----

* http://qiita.com/mriho/items/b30b3a33e8d2e25e94a8
listbox から選択された複数項目を削除

C++で[.net Frameworkのフォーム（Form）のリストボックス（ListBox）](https://msdn.microsoft.com/ja-jp/library/system.windows.forms.listbox.aspx)のオブジェクト`listbox`から選択された複数の項目を削除します。

```cpp
int selectedNum = listBox1->SelectedIndices->Count;
for (int i = selectedNum-1; i > -1; i--) {
  listBox1->Items->Remove(listBox1->SelectedItems[i]);
}
```

デフォルトでlistboxを作成すると単一項目しか選択できないので、以下のコードをlistboxに追加する。

```cpp
this->listBox1->SelectionMode = SelectionMode::MultiExtended;
```
macOSのつんでれんこ（TDEnc2.app）にファイルを放り込むとエラーでセッションが落ちる

`TDEnc2.app`に向かって動画ファイルをドラッグアンドドロップするとbashが立ち上がってよしなにエンコードしてくれる[つんでれんこ]()に久し振りにファイルを渡したら起動すらしてくれなかった（ツンデレ的に）のでメモ

# 環境

* macOS Sierra
* Terminal
    * 普段はiTerm2を使っている
* bash
    * 普段はzshを使っている
* Homebrew

# エラー内容

`"/private/var/folders/k7/（よくわからん文字列）/T/AppTranslocation/（UUID的な文字列）/dtool/TDEnc2.sh" "/Users/（自分のユーザ名）/Movies/pv.mp4";exit`

の後に

`zsh: no such file or directory: /private/var/folders/k7/（よくわからんry）/T/AppTranslocation/（UUIDry）/dtool/TDEnc2.sh`

って出てそのままターミナルのセッションが終わる

# 原因

次の幾つかがパッと思いつくけど詳細は不明。

* 普段iTerm2＋zshを使っててD&DしてTerminal.appが開いた時に環境変数らへんがパスされていない
* Homebrew？

# 解決法

とりあえずドラッグアンドドロップを諦めて自分の普段の環境であるiTerm2＋zshを立ち上げて直接叩きにいきました。

```shell-session
cd Documents/TDEnc2/tool
./TDEnc2.sh （ここに動画ファイルの場所）
```

これでつんでれんこちゃんが復活するはずです。
Raspberry Pi2（ラズパイ2）の購入

## ラズベリーパイっておいしいの?
そもそもラズパイなるものに興味を持ったのは長男でした。「ラズベリーパイ」がコンピュータとどう関係があるのかわからず調べてみると、手のひらサイズで数千円で買えるワンボードコンピュータでありながら、パソコンのような使い方もできれば、制御用コントローラとしての可能性も備えているという優れもの。本来教育用らしいのですが、よくできています。そこにラズパイ用Linuxである Raspbian がリリースされており、Linux入門機としても面白い。昔、UNIXを弄っていた頃を思い出して、ついつい夜更かししてしまいます。

2016年春、大阪日本橋のシリコンハウス共立でラズパイ2とケース、8GB microSDカード、ACアダプタを購入。すでにラズパイ3が発売されていたのですが品切中でした。商品によってはAmazon等の通販のほうが安いけれど、microSDカードの相性などのリスクを考えると専門店で買ったほうが安心かもしれません。そこは各自で判断してください。

## ラズパイ2のセットアップ

ラズパイのセットアップにはモニタとUSBマウス、USBキーボードが必要。それまで使っていたiMacを買い換える際、Mac miniとEIZOの23" モニタにしました。そうすればラズパイをHDMI接続することができ、iMacのマウスとキーボードが流用できるはず。

ところが、そのラズパイ2をセットアップしたのは2016年冬。長男が帰省したときに目敏く見つけて「セットアップしてみよう」。彼は常にMacBookを持ち歩き、ChromebookにKALI Linuxを入れている強者。8GB microSDカードにRaspbianをインストールしてラズパイ2を起動。するはずなのですが電源コードを挿しても基板上のLEDは点灯しません。6枚のアクリル板を組み合わせたケースを分解して、裸基板のまま電源を入れたら起動しました。「このケース、だめじゃん」ということで、やすりで加工して解決。

![IMG_3172.jpg](https://qiita-image-store.s3.amazonaws.com/0/157674/fba393ed-6633-fd6b-75a7-3861a2fc3561.jpeg "IMG_3172.jpg")

電源を入れて立ち上がってきた画面を見てびっくり。これ、X Windowなんだよね。なんか Windows と変わらないように見える。

![screen_img.png](https://qiita-image-store.s3.amazonaws.com/0/157674/ff5269ac-98fd-aaf5-c88e-692b0235ffe4.png "screen_img.png")


最低限のセットアップが済んだら、最後はWiFi経由でVNCサーバ接続したい。まず、WiFiドングルを挿してインストールしてEthernetケーブルを抜きます。

tightvncserverをインストールして、MacOSの「画面共有」アプリで接続。この記事はMac miniで書いているので、ラズパイ上のテキストや画像をキャプチャしたり、カット＆ペーストしたい。そのために autocutsel もインストール。日本語表示するよう設定し、日本語IMEである mozc をインストールしました。

## ラズパイで「Lチカ」

「Lチカ」というのは「LEDをチカチカ」させること。ラズパイ2の GPIO（汎用入出力）ポートを使えば、外部の電子回路を制御できます。ブレッドボードとジャンプワイヤー、LEDと1kΩ抵抗を用意して長男に任せました。

![IMG_3175.jpg](https://qiita-image-store.s3.amazonaws.com/0/157674/3529ddaf-edb3-07ca-9cea-c943d061099e.jpeg "IMG_3175.jpg")

Pythonでコードを書いて試行錯誤。「あ、点いた！」　単純だけど、こういう瞬間がうれしいですね。モチベーションが上がります。

```
import RPi.GPIO as GPIO
import time
# LED blinking
while True:
    GPIO.setmode(GPIO.BCM)
    GPIO.setup(18, GPIO.OUT)
    GPIO.output(18, GPIO.HIGH)
    time.sleep(1.0)
    GPIO.cleanup()
    time.sleep(1.0)
```

ここまで来ると、ラズパイでやってみたいことを色々思いついて、ふたりであーだのこーだの盛り上がりました。

だったら「ふたりで同じラズパイ3を買おう」ということになったのです。ラズパイ3は2よりもCPU性能が上がって、WiFiとBluetooth内蔵で、お値段ほぼ据え置き。このラズパイ2はいずれ組み込み用に使いましょう。

長男は自分たちのホームページを作るといって MacBook に向かっています。「記事はMarkdown記法で書いてね」と指示されて「エディタがほしい」「それなら Kobito がいいと思う」。というわけで Mac mini 上の Kobito で記事を書いています。手軽に体裁を整えることができて便利です。気に入りました。

さて、今後どうなっていくのやら。楽しみです。
多角形を描く関数を作ってみた




![Simulator Screen Shot 2017.01.01 22.38.22.png](https://qiita-image-store.s3.amazonaws.com/0/40693/0f02ce5f-0630-755c-73bc-308e41379717.png "Simulator Screen Shot 2017.01.01 22.38.22.png")
![Simulator Screen Shot 2017.01.01 22.39.32.png](https://qiita-image-store.s3.amazonaws.com/0/40693/5753ab28-73ca-ded2-f0bb-2cd650876c5f.png "Simulator Screen Shot 2017.01.01 22.39.32.png")
![Simulator Screen Shot 2017.01.01 22.39.41.png](https://qiita-image-store.s3.amazonaws.com/0/40693/ff9b62d0-0f4c-dd61-36c4-4e80ef18f480.png "Simulator Screen Shot 2017.01.01 22.39.41.png")
![Simulator Screen Shot 2017.01.01 22.39.52.png](https://qiita-image-store.s3.amazonaws.com/0/40693/ad780d58-8e46-b743-b4d8-8f9db6a8ed82.png "Simulator Screen Shot 2017.01.01 22.39.52.png")

３角形や４角形は用意されてるけど、５角形やそれ以上はどう描けばいいんだ？って思ったので調べてたらいつの間にか１７角形まで調べてしまっていたので関数で使えるようにしたものを公開。

[PolygonSample](https://github.com/rnsm504/PolygonSample/tree/master)


矩型範囲と描きたい多角形を引数で指定すればそのpathを返します。

```
enum Polygon : Int {
    case pentagon = 5   // ５角形
    case hexagon = 6    // 6角形
    case octagonal = 8  // 8角形
    case decagon = 10   // 10角形
    case dodecagon = 12 // 12角形
    case hexadecagon = 16 // 16角形
    case heptadecagon = 17 // 17角形
    case star = 0
}

func polygonPath(rect : CGRect, polygon : Polygon) -> UIBezierPath {

	// 省略 
	
	return UIBezierPath
}


```

CALayer上で使う場合はこんな感じで使えます。

```
    override func draw(in ctx: CGContext) {
        
        ctx.setStrokeColor(UIColor.red.cgColor)
        ctx.addPath(polygonPath(rect: self.bounds, polygon: polygon).cgPath)　// <- 呼び出し
        ctx.drawPath(using: .stroke)
        
    }

```

#### 参考

８角形以上の多角形の書き方ってネットでも資料が少なくて読みづらいのが多かったので、わざわざ本を買ってしまった・・・。

[コンパスと定規の数学: 手で考える幾何学の世界 (アルケミスト双書)](https://www.amazon.co.jp/gp/product/4422214861/ref=oh_aui_detailpage_o03_s00?ie=UTF8&psc=1)
[JAWS-UG CLI] DynamoDB:#7 Dynamodbテーブルのアイテム追加 (Microservice HTTP Endpoint)

AWS CLIを利用して、DynamoDBのテーブルにアイテムを追加します。


前提条件
========


DynamoDBへの権限
----------------

DynamoDBに対してフル権限があること。


AWS CLIのバージョン
-------------------

以下のバージョンで動作確認済

- AWS CLI 1.11.14

```bash:コマンド:
aws --version
```

結果(例):

      aws-cli/1.11.34 Python/2.7.10 Darwin/15.6.0 botocore/1.4.91

バージョンが古い場合は最新版に更新しましょう。

```bash:コマンド:
sudo -H pip install -U awscli
```


0. 準備
=======


0.1. リージョンの決定
---------------------

```bash:変数の設定
export AWS_DEFAULT_REGION='ap-northeast-1'
```


0.2. プロファイルの確認
-----------------------

プロファイルが想定のものになっていることを確認します。

```bash:変数の確認:
aws configure list
```

結果(例):

            Name                    Value             Type    Location
            ----                    -----             ----    --------
         profile       dynamodbFull-prjz-mbpr13        env    AWS_DEFAULT_PROFILE
      access_key     ****************XXXX shared-credentials-file
      secret_key     ****************XXXX shared-credentials-file
          region        ap-northeast-1        env    AWS_DEFAULT_REGION


0.3. DynamoDBテーブル名の指定
-----------------------------

```bash:コマンド:
DYNAMO_TABLE_NAME='microservice-http'
```


1. 事前作業
===========


1.1. アイテムデータの作成
-------------------------

```bash:変数の設定:
FILE_INPUT="${DYNAMO_TABLE_NAME}-item.json" \
        && echo ${FILE_INPUT}
```

```bash:変数の設定:
cat << EOF > ${FILE_INPUT}
{
        "Name": {
          "S": "taro"
        },
        "Description": {
          "S": "sample"
        }
}
EOF

      cat ${FILE_INPUT}
```

JSONファイルを作成したら、フォーマットが壊れてないか必ず確認します。

```bash:コマンド:
jsonlint -q ${FILE_INPUT}
```

エラーが出力されなければOKです。


2. アイテムの登録
=================

```bash:変数の確認:
cat << ETX

        DYNAMO_TABLE_NAME: ${DYNAMO_TABLE_NAME}
        FILE_INPUT:        ${FILE_INPUT}

ETX
```

```bash:コマンド:
aws dynamodb put-item \
        --table-name ${DYNAMO_TABLE_NAME} \
        --item file://${FILE_INPUT}
```

結果(例):

      (戻り値なし)


3. 事後作業
===========

```bash:コマンド:
aws dynamodb scan \
        --table-name ${DYNAMO_TABLE_NAME}
```

結果(例):

      {
        "Count": 1,
        "Items": [
          {
              "Description": {
                  "S": "sample"
              },
              "Name": {
                  "S": "taro"
              }
          }
        ],
        "ScannedCount": 1,
        "ConsumedCapacity": null
      }


完了
====
VSCodeのMarkdownで数式を表示する

## 要約
- VSCodeのMarkdownプレビューはデフォルトで数式のレンダリングをサポートしてない
- [Markdown+Math](https://marketplace.visualstudio.com/items?itemName=goessner.mdmath)プラグインをインストールして表示可能にする

[パッチを当てる解決方法](http://qiita.com/yumetodo/items/1a8d371a20ba9a50eeaf)もありますが、プラグインをインストールするほうがより敷居が低くておすすめです。

## インストール

コマンドパレット（Ctrl+P）を起動してプラグインをインストールします。

```
ext install mdmath
```

ウインドウを再読込みするか再起動すれば使えるようになります。
編集中に`Ctrl+Shift+.`でPreviewが起動して数式が使えるようになっているはずです。

![htmlExport.png](https://qiita-image-store.s3.amazonaws.com/0/67384/592c12c2-9a33-0365-1a83-0efa65b4b9d0.png)
画像は公式ページから引用。

## デフォルトのショートカットキーを置き換える
`Markdown+Math`はデフォルトのPreviewを置き換えているわけではありません。
そのため、従来のショートカットキー（`Ctrl+Shift+V`）を押してもデフォルトのPreviewが表示され、数式は表示されません。

気になる方は以下の設定を`keybindings.json`に書き、既存のショートカットキーで`Markdown+Math`のPreviewを起動するように設定しましょう。

```json
{"key": "ctrl+shift+v", "command":"mdmath.showPreview", "when": "editorTextFocus"}
```