OmniAICreator/Qiita-1.07M huggingface dataset:
How to use Object.defineProperty

Object.definePropertyの使い方をまとめました。
設定プロパティを網羅しているわけではないのでこちらのサイトで確認しましょう

https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Object/defineProperty

# カスタムなsetter, gettterを用意したい場合

現実にあるかどうかは分かりませんがプロパティにマイナスの値が入ってきたらwarningを出力したい場合。

```js
var ValidObject = function(a){
	this._values = {}
	for(let key in a){
		this._values[key] = a[key];
		Object.defineProperty(this, key, {
			enumerable: false
			, configurable: true
			, get: function(){return this._values[key];}
			, set: function(v){
				console.log(this)
				if(v > 0){
					this._values[key] = v
				} else {
					console.warn('This property should be always plus number')
				}
			}
		});
	}
}
var valid = new ValidObject({a: 9, b:8})

valid.a = 90
console.log(valid.a) // 90
console.log(valid.b) // 8

valid.b = -9 //This property should be always plus number

console.log(valid.b) // 8
```

Validationをこのやり方で行うのは少し一般的ではないですが、getter, setterをラップできることでいい感じにロジックを隠蔽できることが利点です。

# 上書き禁止

writable というプロパティを使えばメソッドの上書きを防ぐことができます

```js
function defineProperty(el, key, value) {
  Object.defineProperty(el, key, {
    value: value,
    enumerable: false,
    writable: false,
    configurable: true
  })
}
```

こんな感じのutilメソッドを用意しておけば

```js
var Sample = function(){
    defineProperty(this, 'method', function(a){
        console.log("Don't overwrite this method!!", a)
    });
}

var sample = new Sample();
sample.method = "I want to overwite this method"

sample.method('ok!!') //Don't overwrite this method!! ok!!
```

こんな感じでJavascriptだけでちょっぴり堅牢なメソッドを用意することができます。

# まとめ

ライブラリとか書くときはロジック隠蔽できて、より堅牢にアプリケーションを書けるので便利かも。
でもあんまり普段使わないってのも事実。。。
Ubuntu USBにswap領域を確保する

Ubuntuでメモリが少ない場合に、USBにswap領域を確保する


1.swap状態の確認
```
sudo cat /proc/swaps
```

すでに設定されているようでしたら
sudo swapoff -a
で解除します。

2.USBのパスを確認
```
sudo fdisk -l 
```
USBが
/dev/sda1            8192    30162943    15077376    c  W95 FAT32 (LBA)
であると仮定

2.USBのアンマウント
```
sudo umount /dev/sda1
```

3.USBという名前で、FAT３２でフォーマット
```
sudo mkdosfs -F32 -nUSB /dev/sda1
```

4.USBにswap領域を作成
```
sudo mkswap -c /dev/sda1
```

5.USBのswap領域を有効化
```
sudo swapon /dev/sda1
```

起動時にスワップファイルとして設定されるようにする
```
sudo vi /etc/fstab
```
以下を追加
/dev/sda1 swap swap defaults 0 0


補足

スワップ解除
```
sudo swapoff -a
```

以上
BLE温度計アプリケーション

#はじめに
BLE（Bluetooth Low Energy）温度計センサーの値をスマートフォンで表示するための
Androidアプリケーションを作っています。
初めてAndroidのアプリケーションを作成したので、忘備のために分かったことをまとめておこうと思います。

#使用機器
- BLE温度計センサー

BLE温度計センサーは[浅草ギ研様](http://shop.robotsfx.com/shopdetail/000000000194/)のBLECAST_TMを使用しています。
**コイン電池 CR2032が必要です。**

- 動作環境

動作確認は[FREETEL](https://www.freetel.jp/product/smartphone/priori3s/)のスマートフォンで行っています。
**動作を確認するためにはBLEに対応しているスマートフォンが必要です。**

#開発環境
アプリケーションの作成はEclipseを使用しています。
Version: Luna Service Release 2 (4.4.2)
Build id: 20150219-0600

#アプリケーション
アプリケーションは[GitHub](https://github.com/AkimotoMasane/thermometer)からダウンロードできます。
アプリケーション内で使用している効果音は[魔王魂様](http://maoudamashii.jokersounds.com/)が公開されている素材を使用させていただいております。
配列からnilを削除する

配列からnilを削除する方法

```ruby:test.rb  
a = [1, 2, nil, 4, nil]
p a.compact #=> [1, 2, 4]
p a #=> [1, 2, nil, 4, nil]
```

```ruby:test.rb
a = [1, 2, nil, 4, nil]
p a.compact! #=>[1, 2, 4]
p a #=> [1, 2, 4]
```

nilが入ってない配列にcompact!を使うとnilが返ってくるので注意してね
一意性制約はDB側で実現しなきゃ駄目

###一意性制約をDB側で実現すべき理由

[Railsチュートリアル](http://railstutorial.jp/chapters/modeling_users?version=4.2#sec-uniqueness_validation)に、
一意性制約はコード（Active Record）側ではなくてDB側で実装すべきという注意があったのでメモ。

理由は、以下のようなことが起こり得るから。

1. 登録ボタンが素早く２回クリックされた場合にリクエストが２つ連続で送信される。
2. リクエスト１は検証にパスするユーザーをメモリ上に作成する。<br>
リクエスト２も同様にメモリ上に作成する。<br>
（ここで valid? メソッドにより一意性の検証が行われるが、この時点ではどちらのデータもDBに登録されていないので通過してしまう）
3. 結果、一意性の検証が行われているにも関わらず、同じメールアドレスを持つ２つのユーザーレコードが作成されてしまう。

###対策

DB側で一意性制約を設定する。

```ruby
class AddIndexToUsersEmail < ActiveRecord::Migration
  def change
    add_index :users, :email, unique: true
  end
end
```
IClassFileをエディターで開くときに躓いたので調べた

eclipseのプラグイン開発でjarファイル内にあるClassFileをエディターで開くとき、
通常の.javaファイルと同じように開こうとするとうまくいかない。

.javaファイルの場合は以下のような感じ。

```java
IDE.openEditor(workbenchpage,
    ResourcesPlugin.getWorkspace().getRoot().getFile(javaelement.getPath()));
```

ClassFileのIJavaElementに対してgetPathしてもjarファイルのパスが返ってきてしまうし、
むりくりパスを指定してもエディタがエラーを吐く。

デバッグで起動したeclipseで、手動の操作で.classファイルを開き、
エディタの情報を取得してみると、javaエディタではなくClassFileEditorという
専用っぽいエディタが使用されていた。

更に開いているファイルのパスを取得するとjarファイルとはぜんぜん違う、
一時フォルダ(C:\Users\{user}\AppData\Local\Temp)に
置いてある.classファイルが参照されていた。

もう少し調べて、エディタにファイルを表示したりする場合は
IEditorInputというクラスを使うことがわかった。

IFileEditorInputというインターフェイスがあったので、
ClassFileEditorInputもあるんじゃないかと思って調べてみると、
「InternalClassFileEditorInput」というそれっぽいクラスがあった。

ソースを見てみると、コンストラクタで渡されたClassFileを
一時フォルダにコピーするという処理が書かれていた。

よってClassFileの場合はこうなる

```java
IDE.openEditor(workbenchpage, new InternalClassFileEditorInput(classfile),
    "org.eclipse.jdt.ui.ClassFileEditor");
```
JavaScriptのクロージャについて少し調べた

ある関数内で外のスコープの変数を使用する場合。

```js
var message = "test";
var func = function(){
	alert(message);
};
 
func();		// test
message = "change";
func();		// change
```
funcを定義した後に変数の値を変更するとfuncの実行結果も変わる。

また、関数が定義されたスコープの外でその関数を実行する場合。

```js
var func;
(function(){
	var message = "test";
	func = function(){
		alert(message);
	}
})();
 
alert(message);		// undefined or not defined
func();			// test
message = "change";
func();			// test
```
変数`message`のスコープは7行目で終わっているはずだが
定義したfuncを使うことで値を取得できる。
ということは上のケースもこちらのケースも
関数内で使用した変数がどのスコープからでも参照できているということか。

調べてみるとこの概念をクロージャというらしい。
なるほど。JavaScriptにおけるクラス定義は
このクロージャという概念を使って定義されているわけだ。

ちなみに最初のケースで定義時の変数の値を使用したい場合はevalを使って定義するとできる。

```js
var message = "test";
var func = eval("(function(){" + 
	"return function(){" +
		"alert(\"" + message + "\");" +
	"}" +
"})()");
 
func();		// test
message = "change";
func();		// test
```
文字列で書くとデバッグできなさそうだが、最近のブラウザなら
うまいことやってくれるのであんしん。

クラスでメンバーを定義するときのやりかたを思い出すと
クロージャの概念をうまく使ってevalを使わずにできそうだ。

```js
var message = "test";
var func = (function(){
	this.msg = message;
	return function(){
		alert(this.msg);
	};
})();
 
func();		// test
message = "change";
func();		// test
```
デバッグは問題なくできるとはいえ、evalを使う方法だと可読性が落ちるので
こっちのほうがいいかな。

あ、でもfuncにcallやapplyでthisを渡したいときはダメだな。

thisを使わなくても普通に変数定義したらできた。

```js
var message = "test";
var func = (function(){
	var msg = message;
	return function(){
		alert(msg);
	};
})();
 
func();		// test
message = "change";
func();		// test
```
あれ？クラスのメンバ変数ってthis省略できないんじゃなかったっけ？
クラス定義してるわけじゃないからいいのか？まあいいか。

あ、引数渡しでもいけるな。

```js
var message = "test";
var func = (function(msg){
	return function(){
		alert(msg);
	};
})(message);
		 
func();		// test
message = "change";
func();		// test
```
この辺のスコープの自由さがJavaScriptの自由さって感じがするね。
classからのuseとnamespaceからのuseの違い

# class から trait を use する場合

- 現在属している名前空間が基点になる
- 定義の時点でトレイトが見つからない場合はエラーになる

```php:絶対指定
<?php

namespace mpyw;

class App
{
    use \mpyw\AwesomeLogger\LoggerTrait;
}
```

```php:相対指定
<?php

namespace mpyw;

class App
{
    use AwesomeLogger\LoggerTrait;
}
```

# namespace から何かを use する場合

- 常に**ルート名前空間**が基点になる
- 実際に対象が使用されるまでエラーは検査されない

```php:絶対指定
<?php

namespace mpyw;

use \mpyw\AwesomeLogger\Logger;
use \mpyw\AwesomeLogger\LoggerInterface;
use \mpyw\AwesomeLogger\LoggerTrait;
use function \mpyw\AwesomeLogger\writelog;
```

```php:相対指定
<?php

namespace mpyw;

use mpyw\AwesomeLogger\Logger;
use mpyw\AwesomeLogger\LoggerInterface;
use mpyw\AwesomeLogger\LoggerTrait;
use function mpyw\AwesomeLogger\writelog;
```

つまり，この場合は先頭の `\` は完全に不必要です。書かないことが推奨される，ってどこかで見たような…（情報求む）
ghciでマルチバイト文字をエスケープせず表示させる

ghci 8.0.1の話。
マルチバイト文字が`"\12411\12370"`のようにエスケープされて表示されるが、

```
ghci> "ほげ"
"\12411\12370"
```

これを

```
ghci> "ほげ"
"ほげ"
```

と表示させるようにしたい。

まず`~/MyPrint.hs`を作成：

```MyPrint.hs
module MyPrint (myPrint, myShow) where
-- preparing for the 7.6.1
myPrint :: Show a => a -> IO ()
myPrint = putStrLn . myShow

myShow :: Show a => a -> String
myShow x = con (show x) where
  con :: String -> String
  con [] = []
  con li@(x:xs) | x == '\"' = '\"':str++"\""++(con rest)
                | x == '\'' = '\'':char:'\'':(con rest')
                | otherwise = x:con xs where
                  (str,rest):_ = reads li
                  (char,rest'):_ = reads li
```

シェルでaliasを設定：
（`.ghci`で設定する方がベターだと思うのだが、Haskell超初心者なのでその書き方も分からなかった）

```
alias ghci="ghci -interactive-print=MyPrint.myPrint MyPrint -i$HOME"
```


これで一応はできたのだが、`:load`や`:reload`を使うと元に戻ってしまう。
これは`-interactive-print`の仕様らしい：

>The function can reside in any loaded module or any registered package, but only when it resides in a registered package will it survive a :cd, :add, :load, :reload or, :set.
> https://downloads.haskell.org/~ghc/latest/docs/html/users_guide/ghci.html#using-a-custom-interactive-printing-function

ghciをカラー化するツールもあるので、それをベースにエスケープされた文字列をアンエスケープする方法もある…らしい。
https://wiki.haskell.org/GHCi_in_colour

## 参考

- http://stackoverflow.com/a/14461928/5209556
- [haskell - How to maintain -interactive-print after :load or :reload in ghci? - Stack Overflow](http://stackoverflow.com/questions/37622761/how-to-maintain-interactive-print-after-load-or-reload-in-ghci)
- [#11159 ('-interactive-print myPrint' forgotten after :load or :reload) – GHC](
https://ghc.haskell.org/trac/ghc/ticket/11159)
- [haskell - How to hack GHCi (or Hugs) so that it prints Unicode chars unescaped? - Stack Overflow](http://stackoverflow.com/questions/5535512/how-to-hack-ghci-or-hugs-so-that-it-prints-unicode-chars-unescaped/13113906#13113906)
画像のボケ除去

[スパースモデリング](http://www.kyoritsu-pub.co.jp/bookdetail/9784320123946)第10章の画像のボケ除去：実践例を実装した。[GitHub上のJupyter notebookへのリンク](https://github.com/kibo35/sparse-modeling/blob/master/ch10.ipynb)

結果
--
画像をぼかして雑音を加えた。反復縮小法でボケ補正した。

画像サイズ：$256 \times 256$
ボケカーネル：$\frac{1}{i^{2}+j^{2}+1} (-7\leq i,j \leq 7)$）
雑音レベル：$\sigma^{2}=2$

![deblurring.png](https://qiita-image-store.s3.amazonaws.com/0/114365/03a00b9d-95ea-dd78-9c56-1019b64872f8.png)

SSFはアルゴリズム名。SSF-LSは直線探索を追加、SSF-SESOP-5は逐次部分空間最適化（5個前までの勾配を用いる）を追加したもの。数字はピーク信号対雑音比（PSNR; peak signal to noise ratio）[db]。

アルゴリズム
--
#### 分割可能代理汎関数（SSF; separable surrogate functional）
$$ \mathbf{x_{\rm{k+1}}} = S_{\rho, \lambda / c} (\mathbf{x_\rm{k}} + \frac{1}{c}\mathbf{A^{\rm{T}}}\mathbf{H^{\rm{T}}}(\mathbf{\tilde{y}}-\mathbf{H}\mathbf{A}\mathbf{x_{\rm{k}}})$$

$\mathbf{H}$はボケカーネル。$\mathbf{A^{T}}$はレベル2（非縮小）ウェーブレット変換。$\mathbf{\tilde{y}}$はボケ画像。$\mathbf{x}$はウェーブレット係数。$S_{\rho, \lambda / c}$は縮小の演算子。$c$は規格化定数（$c=1$）。

#### レベル2（非縮小）ウェーブレット変換の例
![wavelet.png](https://qiita-image-store.s3.amazonaws.com/0/114365/e9fe3b39-ce33-b0bb-335b-2fa732120ae1.png)

#### 縮小
L1ノルムをなめらかにした$\rho(x)=|x|+s\log(1+|x|/s)$で$x$の大きさを測ると（s=0.01とする）、$S_{\rho, \lambda / c}$は解析的に求まる。ラグランジュ乗数$\lambda=0.075$とした。
$$ x_{opt}=\frac{(x_{0} - s - \lambda )+\sqrt{(s+\lambda-x_{0})^{2}+4 s x_{0}}}{2} $$

#### 参考
Michael Elad 著、玉木 徹 訳、スパースモデリング、共立出版、第10章
ほぼ静的なウェブサイトでphpを利用した場合のパフォーマンスの違いの目安

CMSなど利用せず、いわゆる静的なHTMLで作成するサイト案件でも、全てのページで共有するヘッダーやフッターなどはPHPが動作する環境であればincludeなどで読み込んで表示するという方法を取ることがあります。

で、そうした場合、パフォーマンスとしてどれぐらいの違いがあるのか、目安程度でよいのでちょっと測ってみました。

ちょうど案件で制作しているサイトで、include4箇所のページで計測しています。

とりあえず比較したものは

* PHPのinclude文で取り込んで表示するもの
* Handlebarsで取り込む箇所をHTMLに組み込んだ上で生成したもの

ということで、それぞれの比較は同じHTMLを出力するようにしました。

計測はabを利用して、iMacのローカル上のapache2(mod_php)、名前解決はhostsに記載しています。どちらもhtmlの拡張子でPHPが動作する環境です。

## 結果

5000リクエストで5回ほどそれぞれ計測しましたがこんな感じでした。

#### includeなし（全てHTML）

```
Requests per second:    591.99 [#/sec] (mean)
Time per request:       1.689 [ms] (mean)
```

#### includeあり（一部PHP）

```
Requests per second:    335.52 [#/sec] (mean)
Time per request:       2.980 [ms] (mean)
```

まあ、とうぜんincludeされる際にディスクの読み込みが発生するので、プログラムなしのincludeでも多少なりとも差が出てくるということですね。これがincludeの回数でまた変わってくるでしょうし、拡張子でPHPとして評価しないようにすればまた変わってくるかもしれません。

ま、当然ながら差があるよってことで。
iOSのWKWebViewの3つのつまずきポイントと解決方法

Safariと同様にスワイプで戻る、進む機能や将来性、パフォーマンスを考えてWKWebViewを導入してみました。
UIWebViewとの違いから、つまずいたポイントがあるので3つ紹介したいと思います。

## 環境
Swift3.0
Xcode8.1 (8B62)

## つまずきポイント
### 1. WKWebViewではPOSTリクエストのHTTP Bodyが無視される
UIWebViewでは以下のようにPOSTの`URLRequest`に対応していました。

```swift
let request = URLRequest(url: url)
request.httpMethod = "POST"
request.httpBody = ...

// OK
let uiWebView = UIWebView()
uiWebView.loadRequest(request)

// request.httpBodyの値が無視される
let wkWebView = WKWebView()
wkWebView.load(request)
```

WKWebViewでは`request.httpBody`に設定した値が無視されます。
そのため、今までBodyにパラメータを付与していた場合、リクエストの構造を変える必要があります。

解決方法としては、2点あります。

1. `URLSessionDataTask`で取得したデータをWKWebViewの以下のメソッドに渡す。
    - `func loadHTMLString(_ string: String, baseURL: URL?) -> WKNavigation?`
    - `func load(_ data: Data, mimeType MIMEType: String, characterEncodingName: String, baseURL: URL) -> WKNavigation?`(iOS9以降）
- HTTP Headerにパラメータを含める

1の問題点は、`backForwardList: WKBackForwardList`が効かなくなることです。
以下のWKWebViewのプロパティ、メソッドが正常に動作しなくなります。

```swift
var backForwardList: WKBackForwardList { get }
var canGoBack: Bool { get }
var canGoForward: Bool { get }
func goBack() -> WKNavigation?
func goForward() -> WKNavigation?
var allowsBackForwardNavigationGestures: Bool
```

Safariのようなスワイプで戻る、進む機能を実装したかったので、1番は諦めました。
僕のやりたかったケースでは2番のHeaderにパラメータを含めることで解決できました。

```swift
let request = URLRequest(url: url)
request.httpMethod = "POST"
request.allHTTPHeaderFields = ...

// OK
let wkWebView = WKWebView()
wkWebView.load(request)
```

## 2. WebView内のTwitter、Facebookボタンが効かない

以下のリンクを参考にしました。
[WKWebViewでtarget="_blank"なリンクが開かない時の対処法 - Qiita](http://qiita.com/ShingoFukuyama/items/b3a1441025a36ab7659c)
[Why is WKWebView not opening links with target=“_blank” - stackoverflow](http://stackoverflow.com/questions/25713069/why-is-wkwebview-not-opening-links-with-target-blank)

`WKUIDelegate` の実装をするのが一番簡単そうです。

```swift
// WKUIDelegateの設定
webView.uiDelegate = self
```

```swift
// WKUIDelegateのメソッド
func webView(_ webView: WKWebView, createWebViewWith configuration: WKWebViewConfiguration, for navigationAction: WKNavigationAction, windowFeatures: WKWindowFeatures) -> WKWebView? {

　   /*
     TwitterのTweetボタン、
     Facebookのいいねボタン、
     target="_blank"のリンクなど、
     新しいウィンドウが開く場合、これを書く必要がある。
     */
    if navigationAction.targetFrame == nil {
            
        webView.load(navigationAction.request)
    }
        
    return nil
}
```

## 3. iOS9でscrollViewのdecelerationRateを変更できない

[Cannot change WKWebView's scroll rate on iOS 9 beta / 9.3 - stackoverflow](
http://stackoverflow.com/questions/31369538/cannot-change-wkwebviews-scroll-rate-on-ios-9-beta-9-3)

上記の投稿に解決方法がありました。

```swift
webView.scrollView.delegate = self
```

としておいて、

```swift
extenstion WebViewController: UIScrollViewDelegate {
    
    func scrollViewWillBeginDragging(scrollView: UIScrollView) {
        
        scrollView.decelerationRate = UIScrollViewDecelerationRateNormal
    }
}
```

とすることでdecelerationRateを設定することができます。
さらに、EXC_BAD_ACCESSでクラッシュすることがあったので、ViewControllerのdeinit時に以下を書いておくと良いと思います。

```swift
deinit {
        
    webView.scrollView.delegate = nil
}
```
エディタに求めるもの

**整理は後で，とりあえず書いておく**

今のところ Atom が良いけど， VS code が結構快適になってきたので、自分の考えを整理しておく

## 利用頻度が高いエディタ
- Linux: vim
- Windows: xyzzy
- Mac: いろいろ使っているけど， vim の頻度が一番高い

## Atom の不満
- **起動が遅い。** これに尽きる

## VS Code の不満
- Atom に比べればかなり速いけれど、まだ少し起動が遅い。
- カスタマイズに関する情報が少ない。
- 他のエディタに比べて、コマンドの挙動が予測に反する。
- 挙動がまだ不安定。日本語入力回りは直ったみたい。(https://github.com/Microsoft/vscode/pull/16187)

# Requirement
- フォントが変更できる
- Winodws, Mac 両方で利用てき，　操作性に違いがない
- 複数のPC間で設定が同期できる
- キーバインドを変更できる
- マクロなど，簡単なテキスト編集機能を組み込める
- すべての機能をキー操作で利用できる
- カラーテーマが利用できる
- ファイルタイプによるタブ幅の変更
- シンタックスハイライトができる
- 起動が十分にはやい
- カーソルキー, home, end 以外でのカーソル移動

# Optional (使えるようになったら便利かも)
- マルチカーソル
- 内蔵 vcs, 今のところコマンドラインで十分
- snippet, 思ったようなコードにならずに修正する方の手間の方が多い
ポータブック + Bash on Windowsでスクリプトを書けるようにするまでにやった事

# ポータブック + Bash on Windowsでスクリプトを書けるようにするまでにやった事

勢いに任せて[投げ売りポータブック](http://www.yodobashi.com/%E3%82%AD%E3%83%B3%E3%82%B0%E3%82%B8%E3%83%A0-KING-JIM-XMC10-PORTABOOK%EF%BC%88%E3%83%9D%E3%83%BC%E3%82%BF%E3%83%96%E3%83%83%E3%82%AF%EF%BC%89-8%E5%9E%8B-Atom-x7-%E3%83%A1%E3%83%A2%E3%83%AA2GB-eMMC-32GB-Windows-10-Home-64%E3%83%93%E3%83%83%E3%83%88-office-mobile-Office365-%E3%83%96%E3%83%A9%E3%83%83%E3%82%AF/pd/100000001002960835/)を買ってきました。ストレージ容量32GBと結構厳しいかと思いましたが、Bash on Ubuntu on Windows上のもろもろと、Chromeを入れても7GB程度残ったので案外戦えそうです。

## 作りたかった環境
* Bash on WindowsでRubyとNode.jsが書ける環境

以下、手順です。

## 1. Anniversary Update入れる
* Windows Update待ってもなかなか降って来なかったので、アップデートアシスタントをダウンロードしました。
* アップデートアシスタントはこちら => https://support.microsoft.com/ja-jp/kb/3159635
* 当然ですが、アップデート前にリカバリメディアを作っておいた方が安全です。
* 2~3時間くらいでインストール出来ました。

## 2. 過去のWindowsを削除する
* エクスプローラ => Windows(C)を右クリック => プロパティと進んで、ディスクのクリーンアップを選択します。

![2.PNG](https://qiita-image-store.s3.amazonaws.com/0/45427/bf00bd7d-7f43-a9d2-d0a2-292dc252a8fc.png)
* システムファイルのクリーンアップを選択すると過去のWindowsや、アップデート時に使ったファイルが見つかるのでこれらを削除します。
* この手順で5GBくらい空き容量が増やせます。

## 3. Bash on Ubuntu on Windowsをセットアップする
* いつも通り、Linux Subsystem for Windowsを入れて、開発者モードを有効にするなどしてセットアップします。

## 4. 日本語が表示できるターミナルエミュレータを入れる
* 今回は、[wsl-terminal](https://github.com/goreliu/wsl-terminal)を入れました。
* 詳しくは@Bakudankunさんの[Bash on Ubuntu on Windowsで256colorする - Qiita](http://qiita.com/Bakudankun/items/5737a123fb894533d48e)によくまとまっています。
* デフォルトのテーマだと色がギラギラして見にくいので好みのものに変えました。
* 今回選んだのは`base16-harmonic16-dark.minttyrc`です。
* フォントは[Ricty Diminished](https://github.com/edihbrandon/RictyDiminished)の14ptを使っています。

![4.PNG](https://qiita-image-store.s3.amazonaws.com/0/45427/782c840c-2c91-23db-8e3e-690b4b29bcf7.png)

## 5. rbenvとnvm入れる
* rbenvとnvmからRuby 2.3.1とNode.js 7.1.0をインストールしました。
* rbenv入れるためにgitが必要です。(`sudo apt install git`)
* Rubyのビルドには1時間くらいかかりました。
* ビルド用のツールは大体入っていないので、[ruby-buildのWiki](https://github.com/rbenv/ruby-build/wiki#suggested-build-environment)に指示されたツールを入れる必要があります。
* nvmとrbenvを入れると、**Bashの起動に20秒くらいかかるようになります**。自分の場合、基本ターミナルは立ち上げっぱなしなのであまり気になりませんが、気になる方は別の方法で入れた方が良さそうです。

以上で、Ruby, Node.jsのコードを軽く書きたい程度の用途には使えるようになります。

## おまけ

### 仮想デスクトップのショートカットキー
* 画面が小さいので、Windows 10の仮想デスクトップを使うショートカットキーを覚えておくと作業が捗ります。
* Win + Tab => 仮想デスクトップ一覧の表示
* Win + Ctrl + D => 仮想デスクトップの追加
* Win + Ctrl + 左右キー => 隣の仮想デスクトップに切り替え

### ストレージの外付けについて
* 本体ストレージが32GBと少ないので、SDかUSBメモリを使って容量を増やしたいケースがあると思います。
* USBポートの部分にはかなり余裕があるので、端子からほとんどはみ出ないタイプのUSBメモリなら刺しっぱなしにできます。
* 通常サイズのSDカードを入れると本体から結構はみ出ます。
* [サンワサプライのMac用microSDアダプタ](http://www.yodobashi.com/%E3%82%B5%E3%83%B3%E3%83%AF%E3%82%B5%E3%83%97%E3%83%A9%E3%82%A4-SANWA-SUPPLY-ADR-MMICRO-Mac%E7%94%A8-microSD%E3%82%AB%E3%83%BC%E3%83%89%E3%82%A2%E3%83%80%E3%83%97%E3%82%BF%E3%83%BC/pd/100000001002833366/)がちょうどいいサイズらしいです。
失われしクラスを求めて

CakePHP3で、自前のヘルパーを実装しようとしたところ、思わぬところで引っかかってしまいました。

# 失敗へ向かう流れ

まず、[このあたり](http://q-neco.hatenadiary.jp/entry/2014/09/12/200839)を見て、だいたいどこへどんなふうに設置すればいいかを把握しました。ただ、コンストラクタに独自処理を差し込みたいと思ったので、コンストラクタのシグネチャを確認した上で、以下のように書きました。

```php:src/View/Helper/HogeHelper.php
<?php

namespace App\View\Helper;
use Cake\View\Helper;

class HogeHelper extends Helper
{
  public function __construct(View $View, array $config = []) {
    parent::__construct($View, $config);
    // これ以降に独自処理を差し込む
  }
}
```

このようにしたところ、ヘルパーを読み込んだ瞬間に落ちてしまいました。

# 何がまずかったのか
エラーログを調べてみれば原因は明らかで、`use Cake\View\View;`を忘れていたために、`__construct`の引数に付けたタイプヒントの`View`が`App\View\Helper\View`と認識されてしまっていました。この「どこかで定義されていると信じている`App\View\Helper\View`クラスのインスタンス」を要求するコンストラクタとなってしまい、`Cake\View\View`が渡されたことでタイプヒント違反となって`TypeError`となってしまったのでした。

# Ruby的に書くには？
Rubyでは、`super`とだけ書けば元のコンストラクタへ与えられた引数がそのまま渡りますが、PHPで「とりあえず、引数をそっくりそのまま親クラスに渡したい」という場合、以下のように書けます。

```php
class Child extends Parent
{
  public function __construct(...$args) {
    parent::__construct(...$args);
  }
}
```

ただ、PHPの場合、シグネチャを拾って情報表示するツールもあるので、今回の例のようにフレームワーク内部で`new`されるクラス以外では、あまり積極的に使わないほうがいいかな、という気もしました（[関連？](https://www.reddit.com/r/PHP/comments/2jy5lx/my_love_of_variadic_functionssplats_continues/)）。
aws_launch_configurationのuser_dataの更新でエラーが出る件の対処


こんな感じのを定義して一度`apply`後、user_dataを修正して再度`apply`すると

```
...snip...

resource "aws_launch_configuration" "config" {
    name                    = "${var.app_id}-as-config"
    image_id                = "ami-374db956"
    instance_type           = "t2.nano"

    key_name                = "home"
    iam_instance_profile    = "${aws_iam_instance_profile.profile.name}"
    security_groups         = ["${aws_security_group.security.name}"]

    user_data               = <<EOT
#cloud-config
...snip...
EOT
}

...snip...
```

こんな感じのエラーを吐く

```
Error applying plan:

1 error(s) occurred:

* aws_launch_configuration.config: Error creating launch configuration: AlreadyExists: Launch Configuration by this name already exists - A launch configuration already exists with the name acceptessa-as-config
        status code: 400, request id: 80fd0b22-a8b6-11e6-b7b8-fb76220c4050
```

散々ググっても出てこなくて、下記のように`create_before_destroy`を指定したら解決するというissueを散々見たものの解決せず。

```
lifecycle {
  create_before_destroy = true
}
```

で、やっと見つけたのが下記のページで。

https://github.com/hashicorp/terraform/issues/2958

> Take the name out of your launch config. If you want to be able to change it, then you need to let it autogenerate a name for you

雑に解釈すると `aws_launch_configuration` から `name` を外せよ。名前指定してるから上書きしようとして再作成できないんだよ。名前を指定しなかったら名前を自動生成してくれるよ、という感じでしょうか。

ということなので、`aws_launch_configuration` の設定から `name` を外し先ほどの`lifecycle`も追加し以下のように。

```
...snip...

resource "aws_launch_configuration" "config" {
    image_id                = "ami-374db956"
    instance_type           = "t2.nano"

    key_name                = "home"
    iam_instance_profile    = "${aws_iam_instance_profile.profile.name}"
    security_groups         = ["${aws_security_group.security.name}"]

    user_data               = <<EOT
#cloud-config
...snip...
EOT

    lifecycle {
      create_before_destroy = true
    }  
}

...snip...
```

そうしたら動いた！！！
Cocoapodsをver1.0.0にあげたけど0.39.0と表示される

すでに入っているpodのパスを確認してください。

```
% which pod                                                                                                                          [17:47:59]
/Users/jumbo/.rbenv/shims/pod
```

rbenvで管理しているgem経由で入れた場合、上記が正しい。
ただ何らかの理由でrbenv使わず入れていると

```
% which pod                                                                                                                          [17:36:28]
/usr/local/bin/pod
```

この辺にあるので削除してください、これでオッケー

```
% rm -rf /usr/local/bin/pod
```
第1回 CSSのこれやだ選手権 2016秋

# marginとかいうやつ

（間違いなく語弊を孕みながら申し上げ奉りますが）marginが嫌いであります！！！！！！！！

！！！！！！！！！！１

！！！！！！

:disappointed:

おかげでBootstrapとかNormalize.cssとか、扱うのが精神的に厳しいですね。
すべての元凶はmarginである:imp::imp:

最近BEMやらReactやらAngularやらでコンポーネント分割が勢力を拡大してますよね。
というよりある程度コンポーネントに切り出しての汎用化は従来もやってたことだと思うのですが、ひたすらmargin嫌になりません？なりません？？？これは僕だけなのか？？？

一方でプログラミング分野では関数型が注目を集めたり、それこそReactでもImmutableだったりPureみたいな単語がよく見受けられるし、そういう概念が注目を浴びるのはいたって同意の気持ちしかないのですが、もうちょっとCSSの世界でそれが提唱されてもいいのではないかと。。。
コンポーネント分割したとき、そのコンポーネントが一番外側にmarginもってるのって悪じゃないですか！？！？！？！（大声）
コンポーネント界の目線になったつもりで言えば、まさに副作用にか思えなくて、以前からずっと嫌悪してました。
コンポーネント内で、（BEMでいうとElementにあたるものが）marginを持つのは全然構わないです。あくまでコンポーネント外に影響を及ぼさない範囲であれば。
ただし他のコンポーネントとの余白を作りやがるもっとも外側のmargin、お前はダメだ！！！！！！！！（大声）
ダメなんだああああああああああ

# おわり
他にもあると思ったら意外とスッキリして満足してしまいました。

（完）
pLaTeXでdvipdfmxを使ってPDF化するときに図をなるべくきれいに入れる

pLaTeXで論文などを書くときに，UMLやパワポの図をなるべくきれいに（＝ピクセル画像の張り込みではなくベクタ画像として）貼り込みたくなります．

# 基本
アプリケーションが生成したPDFから周囲の余白を取り除いたPDFを生成し，それを\includegraphicsします．基本の手順は以下の通り．

1. アプリケーションでPDFを生成する  
    PDF入稿の場合，フォントを埋め込んでおくこと，という指示がなされていることがほとんどです．フォントのライセンスを気にすると，IPAフォントなど埋め込みが許可されたフォントを使いたくなります．  
   しかし，Windows10に付いてくるMicrosoft Print to PDFでは，MSフォント以外のフォントの場合，一部の文字が消えてしまったり，正しく出ない場合があるようです．そのため，その他のPDFプリンタドライバ（CubePDFなど）を使います．なお，CubePDFは，デフォルトでフォントを埋め込んでくれます．
1. pdfcropを使って，周囲の余白を取り除く
A4等のサイズでプリントアウトされますので，texliveに含まれているpdfcropをつかって，周囲の余白を取り除いたPDFを生成します．  

    ```shell-session
    % pdfcrop input.pdf output.pdf
    ```
3. 生成したPDFを貼り込む
graphicxパッケージを使って，ドキュメント中に生成したPDFを貼り込みます．
    
    ```latex
    \usepackage[dvipdfmx]{graphicx}
    ...
    \begin{figure}
        \includegraphics{hogehoge.pdf}
    \end{figure}
    ```

# できればmake一発で
しかし，いろんなツールを使って図を作成していると，更新した図で貼込み用のPDFを更新するのを(〆切間際に限って)忘れてしまいがちです．makeコマンドで，図の元データを更新すれば自動的に貼込み用PDFを生成してくれればベストです．

## PlantUML
PlantUMLでは，ライブラリをいくつか追加すればPDFを直接出力できるようですが，うまくいかない，というブログも見かけます．追加ライブラリなしでPDF化するには，PlantUMLではSVG形式で保存しておき，inkscapeでPDF化すると，きれいな図が生成されます．

```shell-session
% java -jar $(PLANTUMLPATH)/plantuml.jar -charset UTF-8 -tsvg original.puml
% $(INKSCAPEPATH)/inkscape -f original.svg -A output.pdf
```

なお，日本語の場合，ソース内で，フォントを明示的に設定しておきましょう．

```text
@startuml
skinparam defaultFontName IPAexGothic
...

@enduml
```

## PowerPoint
1つのpptxファイルに1つの図，という前提であれば，[ここ](http://superuser.com/questions/641471/how-can-i-automatically-convert-powerpoint-to-pdf)に載っている下のほうのVBAスクリプトを，例えばpptpdf.vbsという名前で保管して使うと，以下のようにして変換できます．ただし，PDF出力の時にデフォルトで枠線がついてしまうので，スクリプトの下から4行目のobjPresentation.ExportAsFixedFormatの第4引数を，msoFalseに変更してください．

```shell-session
% cscript.exe $(SCRIPTPATH)/pptpdf.vbs input.pptx output.pdf
```

なお，プリンタドライバと同様，PowerPointのPDF保存は変なPDFを生成する場合があるので，本来は，PDFプリンタドライバへの出力にしたほうがよいでしょう．

## Excelグラフ
PowerPointの時と同様に，VBAスクリプトで可能です．

シート中のChartオブジェクトにも，上のスクリプトと同様ExportAsFixedFormatがあります．目的のグラフのChartObjectをActivateした上で，ChartObject.Chart.ExportAsFixedFormatを実行すればPDFが生成されます（ExcelでのPDFのformattypeは0なので注意）．

例えば，ブック内全てのグラフをPDF化して出力する場合は，こんな感じになります．

```vbnet
Const xlFixedFormatTypePDF = 0  ' PDF format

Dim i
Dim j
Dim objCo
For i = 1 To objBook.Worksheets.Count
    For j = 1 To objBook.Worksheets(i).ChartObjects.Count
    	Set objCo = objBook.Worksheets(i).ChartObjects(j)
	objCo.Activate
	objCo.Chart.ExportAsFixedFormat xlFixedFormatTypePDF, outputFile & objCo.Name & ".pdf"
    Next 
Next
```
Githubのリリースページからダウンロードをさせたいとき、Nutsを使うと便利

### 概要
Githubのリリースページからソフトウェアやソースをダウンロードさせたいといったことがあると思います。
そういうときにNutsを利用すると便利です。

### なにができるか
[Nuts](https://github.com/GitbookIO/nuts)
を使用するとGithubのリリースページから指定した条件のファイルをダウンロードするといったことが簡単にできます。

例えば、nutsをherokuでホストした場合、
`https://your-app.herokuapp.com/download/osx`
というURLにアクセスすると、OSX用の最新版のdmg/zipのダウンロードウィンドウが開きます。
OSは指定しなくても自動で判断してくれます。

### ユースケース
特に有用なケースだと思われるのが、Electronアプリのダウンロード/アップデートをする場合です。
Electronのauto-updaterのマニュアルにもNutsの名前が出てきます。
[auto-updater](https://github.com/electron/electron/blob/master/docs/api/auto-updater.md)

アップデートの場合は、
`https://your-app.herokuapp.com/update/osx/1.0.0`
といった形でURLを指定します。

### デプロイ
最もお手軽なherokuにデプロイする場合の方法です。

1. Githubに`Deploy to heroku`ボタンがあるのでクリック。
1. 設定を行っていきます。注意点のみ列挙します。  
 * `GITHUB_REPO`にはURLではなく`ユーザ名/リポジトリ名`といった形で記載。
 * `API_USERNAME`、`API_PASSWORD`は適当に入れておく。  
 (開発者向けのAPIにアクセスする場合に使用する。)
1. デプロイする。

簡単だ〜〜〜:relaxed:

### ドキュメント
[Nuts Documentation](https://nuts.gitbook.com)
ここを参照してください。

### その他
* 現状、バックエンドはGithubしか対応していないけど、S3とかも可能  
(プルリクは送られているが取り込まれていない)
Windows10とUbuntu14.04デュアルブートGPU搭載PC→Ubuntu再インストールでシングルブート化

#背景
Windows10とUbuntu14.04のNVIDIA GPU搭載デュアルブートPCにおいてUbuntu側だけスピーカから音が出ず試行錯誤の末、

```
　% sudo apt-get purge alsa
　% sudo apt-get autoremove
　
　% sudo reboot
　
　% sudo apt-get purge pulseaudio
　% sudo apt-get install pulseaudio
　
% sudo reboot
```
とやったら見事にUbuntuが壊れたので再インストールすることにしました。
この機会にデュアルブートは解消してUbuntuマシンのVMWare上でWindowsという構成にします。

#予定手順
- 念のためWindows10の回復ディスク作成
- インストールせずにトライ（try ubuntu without install）
- 動くことが確認できてからインストール


直接デュアルブートの片割れに再インストールする方法もあるようです
[デュアルブート時のUbuntu再インストール](http://linux-suomi.net/modules/letsubuntuyuiat/tips/tips_rinstall.html)
が、Grub再構成失敗とかしたら取り返しつかなさそうなのでwindowsリカバリも用意。

また一般的なUbuntuのインストール手順については各種記事がありますので
[Ubuntuのインストールの仕方](https://allabout.co.jp/gm/gc/427280/)
など参考にして下さい。

#windows10 64bit バックアップディスク作成
使わなくて済むことを祈りますが、念のため下記を参考に。
[Windows10 では回復ドライブとシステム修復ディスクの両方が作成できる](http://fanblogs.jp/honeycome/archive/72/0)


#Ubuntu14.04 try ubuntu without install
ひとまずbiosでUSBからの読み込みをトップにして始めます。
まずはいきなりinstallせずに試しますが、ここで注意！
今試そうとしているマシンにはNVIDIA GTX960が搭載されています。
GPUが搭載されていると「try ubuntu without install」を
選択したあと画面が真っ暗になり何も始まりません。
（「install ubuntu」選択しても同様）

もしそうなってしまったら一度強制終了してから再びメニュー画面出してください。
そこで
「try ubuntu without install」にカーソルを合わせて「e」キーを押します。
するとつらつら設定が出てきますが、

`quiet splash`
となっている箇所を

`nomodeset`
に置き換えてください。
これで無事ubuntuが起動します。
参考：[空の内蔵HDDにUbuntu14.04をインストールしてマルチブート(nvidia GPU使用)](http://may46onez.hatenablog.com/entry/2016/02/04/201701)


無事起動したことを確認できた後、
Ubuntuのインストールを開始します。左端のメニュー（恐らく上から２つ目）のインストールを選択して開始。途中、
「Ubuntu 14.04.4 LTSを削除して再インストール」
という項目がありますので、ありがたくこれを選択させていただきます。
次に聞かれるパーティションについてはマシンにおまかせです。
（マニュアルを選んで自分で設定すればwindowsも潰さずにすむのかな）

全てのインストールが終了すると再起動を求められますのでその通りに再起動します。
ここからまた注意！
再起動しようとするのですが、今度は何も表示が出ないまま真っ暗な画面に…

先ほどと同じでGPUの問題のようです。ここでは電源ボタン長押しで一度終了してから再び起動、
今度は「esc」キーを何度か押しているとメニュー画面（GRUB画面）が表示されます。
ここまできたら先ほどと同じように「ubuntu」にカーソル合わせて「e」キーを押して
`quiet splash`　→　`nomodeset`
と編集してF10で起動できるはずです。

で、ここからソフトウェアのアップデート走らせたのですが、出るわ出るわエラー検知。
ということでもう一度上の手順繰り返してUbuntu全て入れ直しました。
すると初回の起動時に一度検知しただけであとは出なくなったのでインストールはこれで完了とします。

#NVIDIA GPUの対応
次に今の状態たど立ちあげる際に毎回「esc」キー押して設定の編集しなければならないのでnvidiaのドライバをきちんと入れます。入れれば毎回編集する必要もなくなります。

#手順概略
- http://www.nvidia.co.jp/Download/index.aspx?lang=jp から自分の環境に合ったドライバダウンロード
- 「ctr」 + 「alt」 + 「F1」でGUI画面に移行
- 各種設定および実行

```
sudo apt-get purge nvidia*
sudo service lightdm stop
sudo chmod 755 ~/Downloads/NVIDIA-XXXX  (※Downloadしたディレクトリおよびファイル）
cd Downloads
sudo ./NVIDIA-XXXX
```
※注意：もしフォルダ名が「ダウンロード」「デスクトップ」など日本語になっていたら「downloads」「desktop」など英語に変えておくことをおススメします。GUI画面では `cd ダウンロード` など日本語が使えません。（方法あるのかもしれませんけど、私はさっさとフォルダ名変えました。）

最後に`sudo reboot`などで再起動してやればすんなりログイン画面にいけるはすです。
参考：
[空の内蔵HDDにUbuntu14.04をインストールしてマルチブート(nvidia GPU使用)](http://may46onez.hatenablog.com/entry/2016/02/04/201701)
[Ubuntu 12.04 LTSでXwindowの停止と起動](http://blog.goo.ne.jp/takuminews/e/69b671756edc69f494874523c1e7b8ac)
Go言語でハマったNつのこと

この記事では、Go言語でコードを書いていて、（主に勘違いにより）ハマってしまったことについて紹介します。

# json.Unmarshalが成功してるのにデータが入ってない！←それPublicにしないとだめだよ

下記のコードは[json パッケージ](https://golang.org/pkg/encoding/json/#Unmarshal)からExampleを抜粋、改悪したものです。

``` Go:コード例（NGパターン）
package main

import (
	"encoding/json"
	"fmt"
)

func main() {
        var jsonBlob = []byte(`[
		{"Name": "Platypus", "Order": "Monotremata"},
		{"Name": "Quoll",    "Order": "Dasyuromorphia"}
	]`)
	type Animal struct {
		name  string `json:"Name"`  // NG. name -> Name
		order string `json:"Order:` // NG. order -> Order
	}
	var animals []Animal
	err := json.Unmarshal(jsonBlob, &animals)
	if err != nil {
		fmt.Println("error:", err)
	}
	fmt.Printf("%+v", animals)
}
```

これ、当然データがanimalsに入りません。jsonパッケージから、Animal.nameとAnimal.orderが参照できないからです。

# req = http.NewRequest(http.MethodGet, anyUrl, queryParameter)でクエリ付きGetリクエスト←クエリはreq.URL.RawQueryに登録しないとだめだよ


``` Go:コード例（コメントにNGパターン）
// クエリパラメータの作成
v := url.Values{}
v.Add("q", query)

// NG クエリパラメータをrequest bodyにセット。
// req, _ := http.NewRequest(http.MethodGet, urlStr, strings.NewReader(v.Encode()))
// "普通の"Getリクエストはrequest bodyなし
req, _ := http.NewRequest(http.MethodGet, urlStr, nil)

// クエリパラメータは直接RawQueryにセット
req.URL.RawQuery = v.Encode()
```

# $ any-go-tool -s='\t'でタブ文字を渡す←ツール側で'\t'を処理する必要ありますよ || -s=$'\t'

コマンドラインツールを作っていて、引数に'\t'（タブ文字）や'\n'(改行)などエスケープ記法の値を渡して利用する場合、ツール側にそれらの文字を扱う実装が必要になります。またはBashの[ANSI C like strings](http://wiki.bash-hackers.org/syntax/quoting#ansi_c_like_strings)機能などを使って、タブ文字の文字コードを渡せば、実装なしにタブ文字などを扱えます。

``` bash:コマンド実行例
# $'string'のフォーマットで、Bashはエスケープ記法の文字列を処理してからアプリに渡す
$ any-go-tool -s=$'\t'
```

# ハマり次第適宜追加します。
Smart Device Link(スマートデバイスリンク）の情報

Smart Device Link(SDL:スマートデバイスリンク）の情報をまとめる。
※日本語情報があまりないので公式ドキュメントの意訳となります

# Smart Device Linkとは
![Smart Device Link LOGO](https://developer.ford.com/uploads/SDLimageLarge.png)
スマートフォンと車載器を連携するためのオープンソース仕様。
車載器向けのライブラリと、iOS、Android向けのSDKが提供されている。

もともとはFordのAppLinkという車載器向けアプリを作る基盤だったものを2013年にSmart Device Linkとして公開された。


![Smart Device Link LOGO](https://developer.ford.com/uploads/SDLFlow.png)
スマートフォン、車載器それぞれOSが異なっていてもSmart Device Linkをサポートしていれば、自動車でナビ、音楽、インターネットを楽しむことができる

##　概念
車載器がSmart Device Linkに対応していれば、Smart Device Linkに対応したスマートフォンのアプリが車載器および車のインターフェースと通信することができる。

### 車両メーカーまたはナビメーカ
車載器がSmart Device Linkに対応するためにSDL Coreというライブラリ提供されている
<img width="1048" alt="スクリーンショット 2016-11-12 18.03.35.png" src="https://qiita-image-store.s3.amazonaws.com/0/47064/6956fb17-655e-5ccb-a02f-234549975ae9.png">
上の例だと、APPLINK(Ford向けの車載器アプリインフラ)からMYAPPSを作ることができる、またCONNECT LINK9000を新しく作ることもできる
※https://d83tozu1c8tt6.cloudfront.net/media/resources/sdl_overview_and_update.pdf

### スマートフォンのアプリの開発者
SDLを実装しアプリであれば、複数の車両メーカーまたはナビメーカの車載器に提供できる
<img width="758" alt="スクリーンショット 2016-11-12 18.03.47.png" src="https://qiita-image-store.s3.amazonaws.com/0/47064/4eba1b20-56cd-5442-706c-2907f2ca74a6.png">
上の例だと、PANDORA(インターネットラジオ）がSDLをサポートしたアプリを作ればAPPLINK(Ford向けの車載器アプリインフラ)以外のMYAPPS（まだ存在しないけど）やCONNECT LINK9000（まだ存在しないけど）でも動く
※https://d83tozu1c8tt6.cloudfront.net/media/resources/sdl_overview_and_update.pdf
※今の所 SDLをサポートしているのはFordのAPPLINKだけ

## Smart Device Linkの主な構成要素

- SDL Core
    - 中心的な構成要素
    - 車両メーカーまたはナビメーカが車載器に実装するソフトウェア
    - SDL Coreが車載器とスマートフォン上のアプリとのアクセスを可能にする
- SDL Server
    - SDLサーバーはオプション
    - 車載器で提供するアプリの方針を更新したり、使用できるアプリの情報を集める
    - 車両メーカーまたはナビメーカが実装
- iOS and Android SDK
    - iOSとAndroidの開発を支援するためのSDKライブラリ
    - アプリ開発者が利用する
- SHAID
    - Super Helpful Application IDの略
    - アプリに関する情報をSmart Device Linkのエコシステム上で同期を助けるマイクロ・サービ群
    - 車両メーカーまたはナビメーカが実装する（とおもわれる）

## できること
- 車両のインターフェースを利用
    - 音声認識
    - テキストtoスピーチ
    - ボタン（タッチスクリーンを含む）
    - ディスプレイ
    - オーディオ
- 車両情報の取得
    - シートベルト位置
    - ギア情報
    - エアバックの状況
    - その他
    
## 類似規格
iOS用のCarPlayとAndroid用のAndroid Autoがライバル規格と考えてよい。
大きな違いとして、CarPlayはiOS、Android AutoはAndroidのみをサポートしているが、Smart Device Linkは、両方のSDKを提供している、またSDKははないがそれ以外のiOS、Android OS以外のスマートフォンからも利用できそう。

##対応状況

| 規格名      |    トヨタ |ホンダ |日産 |マツダ |三菱 |スバル |スズキ |
|:-----------------|:--|:--|:--|:--|:--|:--|:--|:--|
| SDL     |    ○ |||○  ||○  |○  |○ |
| CarPlay          |   ○ |○|○|○  |○|○  |○  |      
| Android Auto       |    |○|○| ○ |○|○  |○  |


※1 2018/01　スマートデバイスコンソーシアムに加盟しているもの
※2 2016/11現在対応車両販売中

# ドキュメント
## 仕様書
- https://www.smartdevicelink.com/docs/

## SDK
- SDL Core
- https://www.smartdevicelink.com/resources/

# 関連リンク
- Ford
    - https://developer.ford.com/pages/sdl
- Wikipedia
    - https://en.wikipedia.org/wiki/SmartDeviceLink
-CarPlay
    - http://www.apple.com/jp/ios/carplay/
- Android Auto
    - https://android.com/auto/
- Genivi Project
    - https://at.projects.genivi.org/wiki/pages/viewpage.action?pageId=11568933
クリック猿でも1打鍵だけすればEV3RTがビルドできる環境

# 前口上

ETロボコンでも使われている EV3RT ですが，TOPPERS プロジェクト(というか OSS)の製品にありがちなことに，開発環境の構築が面倒です。
やりたいことは EV3RT のアプリケーションの開発のはず。
環境の構築なんてしたくありませんよね? 楽をしましょう。

ということで，先日は[300打鍵以内でEV3RTをビルドする](http://qiita.com/monamour555/items/4bf28b7a775a17f33a14)方法をご紹介差し上げました。
でも，キーストロークは少なければ少ないだけ嬉しい。ですよね?

本記事では，打鍵数を極限まで減らした例をご紹介差し上げます。

# 環境

[Eclipse/Che](http://eclipse.org/che/) を使います。

## Che ってどんな開発環境?

Che については本家の説明を読んでいただくのが確実だと思いますが，いわゆる Cloud IDE という分類のソフトウェアです。

「あー、Eclipse かー、なんか重そうで嫌だなぁ」
と思った読者の方、安心してください。
Eclipse Foundation が管理しているだけで，全くの新規設計のエディタです。 Eclipse との互換性は、見た目も含めてほとんどありません[^e]。むしろ機能的にシンプル過ぎてがっかりするかもしれません[^tm]。

[^tm]: 読者が古くから小規模組込みの経験者なら「昔三菱が出していたTMと同じくらいの機能」というと想像して頂けるでしょうか?

[^e]: 内部構造には，Eclipse を参考にしていると思われる部分もあります。

ざっくり説明すると、下記のような着想で作られています。

* 統合開発環境(IDE)のUIにWebブラウザを用いる。
* ビルドやワークスペースの管理は別途立てるサーバに任せる。

なので、クライアント側は Web ブラウザだけあれば十分です。実際、本記事からリンクしたスクリーンキャストは ChromeOS 上の Chrome で撮っています。

サーバの中身は Docker コンテナ群で，上手く設定するとマルチテナントに対応できたりします。

また、複数ユーザが同じURLでワークスペースを開き、同時に編集できます。
ペア・プログラミングのときに顔を近づけなくて済むので嬉しく、リモートデスクトップのように画像を転送するわけではないので通信負荷も軽めです。

# 手順

Web ブラウザを使うということで、GUI 環境になります。
文字で説明するのは難しいので、動画に頼ります。
Che のインストールや設定は終わっていて、URL を叩いて Che の Dashboard が見えているところからの手順です。

## ワークスペースを作る

ワークスペースを作る際に、Stack として `EV3RT` を選択します。
Stack には、ワークスペースへの各種設定情報が書かれています。

「お? Eclipse/Che には最初から設定が入っているのか!?」と小躍りした読者には申し訳ないですが、__EV3RTのようなニッチな環境の設定が最初から入っているはず無いです__。筆者がいろいろ設定したので一覧に出ています。
ただしその設定は，さほど難しくはない JSON ファイルを書くだけです。(本稿の範囲を超えるので詳細省略)

ワークスペースを作ると、作業環境となる Docker コンテナのイメージが無ければダウンロードされ、あればコンテナが起動します。

[![Workspace の作成動画](http://img.youtube.com/vi/3E34M7ePJM4/0.jpg)](http://www.youtube.com/watch?v=3E34M7ePJM4)

## プロジェクトを作る

続いてワークスペース内にプロジェクトを作ります。(この辺りの構造は Eclipse と似ています。)
途中でプロジェクト名を入力する必要があります。
ここで痛恨の1打鍵が必要です。

[![Project の作成動画](http://img.youtube.com/vi/-yb_D-M3QFY/0.jpg)](http://www.youtube.com/watch?v=-yb_D-M3QFY)

## ソースコードを GitHub から clone してくる

Che には、開発中のワークスペースに対して、コマンドを発行する機能があります。このコマンドは，動的な設定もできますが， Stack に書くこともできます。そして，今回は Stack に既に書いてあります。
よって，ドロップダウンリストから選択して実行ボタンを押すだけです。

[![GitHub からソースコードをclone動画](http://img.youtube.com/vi/HvAQhKmeVJc/0.jpg)](http://www.youtube.com/watch?v=HvAQhKmeVJc)

## その後の作業

GitHub から clone した後のビルド作業は，もう察していただけるでしょう。コマンドに書いてありますので，ソースコードの clone と同じように選んで実行ボタンを押すだけです。

[![カーネルコンフィギュレータのビルド動画](http://img.youtube.com/vi/mMDBEgk_s4A/0.jpg)](http://www.youtube.com/watch?v=mMDBEgk_s4A)

[![uImageのビルド動画](http://img.youtube.com/vi/ApVftPgEEQI/0.jpg)](http://www.youtube.com/watch?v=ApVftPgEEQI)

[![uImageのビルド動画](http://img.youtube.com/vi/ljmIrqTbguk/0.jpg)](http://www.youtube.com/watch?v=ljmIrqTbguk)

あとは，Project Explorer のツリーを開いてファイルが生成されているのを確認するなり，必要ならローカルにダウンロードするなり，アプリケーションの開発を始めるなりしてください。

# 余談

「打鍵数を減らすためにサーバを立ち上げたり設定ファイルを書いたりしているのって，むしろ手間が増えているのではないか?」というツッコミは却下です。:-1:

サーバを立ち上げるのはつらい，という方々に対して現実的な提案を挙げるとするならば…。
例えば Eclipse の開発主体である Codenvy 社が Che を土台にしたクラウドIDEのサービスを行っています[^1]。1アカウント5名までなら無料です。
Codenvy 以外にも何らかの形で Che を取り入れた SaaS/PaaS 提供業者が登場する可能性は高いと思われます。

「IoT がバズっている割に，組込み系の方々はなかなか Web 系の成果物に触れる機会がない。」
「Web 系の方々は組込み系の環境構築で挫ける。」
そんな声をしばしば耳にしますので，こんな解決方法もありますよ，というご紹介でした。

[^1]: というか，Codenvy 社が作っていたクラウドIDEをOSS化したものがCheというほうが実態に近い。
失敗しないcommandの呼び出し方 | Tips for Internship 1

---
#### [ Tips for Internship ] について

[KARAPPO](http://karappo.net)にインターンの学生さんが入ってきたので、教育過程で出てきたTipsのうち、一般的なことはここに書いていってみようと思います。間違ったことを教えていたら恥ずかしいのですが、自分の気持ちを引き締めるために公開してみます。なにかおかしなことがあれば、指摘していただけるとありがたいです。

---

# 失敗しないcommandの呼び出し方

rbenvを使用していて、ブロジェクト毎のgemはbundlerでプロジェクトフォルダ下にインストールしている時、普通に`rails s`とか`bundle install`とかしても、意図したcommand（またはその依存関係にあるcommand）が呼び出せないことが原因で、エラーが出ることがあります。
これは、rbenvやbundlerを使うと同じ名前のcommandがローカルマシン内に複数存在することが原因の一つです。（本当は、PATHの設定とかちゃんとすればうまくいくんだとおもいますが…）
こういう時、「rbenvで指定したrubyを使って」+「（そのruby環境にインストールされた）bundlerで管理している◯◯を呼び出す」という意味で`rbenv exec`+`bundle exec`とすれば、明示的にcommandの指定ができるので、予め毎回これを付けておくと変なところで詰まりにくくなります。

```
rbenv exec bundle exec ◯◯
```

ただ、毎回打つのは面倒なので、ショートカットを割り当てておくと便利です。

`~/.bashrc`に下記を追加

```.bashrc
# rbenvとbundlerを使った環境用
function re   { rbenv exec $@ }
function reb  { rbenv exec bundle $@ }
function rebe { rbenv exec bundle exec $@ }
```

これで、

```
re ◯◯
```

と打てば、

```
rbenv exec ◯◯
```

が実行でき、

```
reb install
```

と打てば、

```
rbenv exec bundle install
```

と同じ意味に。さらに、

```
rebe rails s
```

で、

```
rbenv exec bundle exec rails s
```

が実行できます。

---

＜余談＞

`.bashrc`によく使うcommandのエイリアスを書いておくと、便利です。

参考までに[僕の設定ファイルの該当部分](https://github.com/naokazuterada/dotfiles/blob/65660efd5bc7937a0b164329bccdaaa8fe239c00/zsh/zshrc#L62-L110)です。（bashじゃなくてzshを使ってるので`.bashrc`ではなく`.zshrc`という名前になってますが、大概同じ記述で大丈夫なはずです）
jupyterメモ

jupyterのメモです。Macで使用しています。

こちらがバージョンかな？

```:バージョン
The version of the notebook server is 4.2.1
```

# jupyterの起動

```bash:起動
jupyter notebook
```
jupyterが起動しブラウザからタブが開きます。


# ショートカット
使いそうなあたりを確認しました。

|    ショートカット      |    動作    |
|:-----------------:|:------------------:|
|  ESC |        コマンドモードになる        |
|  y |      コードモードになる      |
|  m |      マークダウンモードになる      |
|  Enter |      編集モードになる <br> (編集モードでは改行)    |
|  Ctrl + Enter |  コードを実行  |
|  Shift + Enter |  コードを実行して、セルを新規追加  |
|  a |      セルを上に新規追加      |
|  b |      セルを下に新規追加      |
|  dd |  セルの削除  |
|  c |  セルのコピー  |
|  v |  セルのペースト  |
|  k |  上のセルの移動  |
|  j |  下のセルの移動  |

vimのショートカットに似ていると思いました(☝ ՞ਊ ՞)

# コマンドを実行
コマンドモードで`!`をつけるとコマンドを実行できます。

```bash:コマンドを実行
!使用したいコマンド
```
以下は実際にコマンドを実行した例です。

```bash:コマンド実行例
!pwd
!ls -al /root/notebook

/root/notebook
total 32
drwxr-xr-x  5 root root 4096 Nov 12 08:40 .
dr-xr-x--- 15 root root 4096 Nov 10 15:30 ..
-rw-r--r--  1 root root 1525 Nov 12 08:34 Untitled.ipynb
-rw-r--r--  1 root root 1117 Nov 12 08:35 Untitled1.ipynb
```

# jupyter内で ImportError
jupyter内で、pandasを入れようとしたら,No module エラーががでました。

```
ImportError: No module named pandas
```
これは環境（ボクの場合はMac）にpandasが入っていないとjupyterから使用できないようです。
Macにpandasを淹れます。

```
sudo pip install pandas
```
今度はImportErrorが消えました。


# jupyter 内のセル操作
`In` などが思うように動作しないときは Kernel から行くのが有用でした。

- Kernel
    -  Restart
    -  Restart &amp; Clear Output
    -  Restart &amp; Run All
    -  Reconnect
JavaScriptとかC#でstaticローカル変数の代わり

staticローカル変数とは
===================

C言語とかVB.Netとかには存在する。あとVBAにもあったような気がする。
JavaとかC#とかにはないらしい。

詳細はググれ(なげやり)

私の認識は、
**グローバル変数みたいにずっと残るけど、スコープはグローバルじゃなくてローカルな変数**
というものです。

スコープは小さくできるなら小さくするのが鉄則だと思うので「値をずっと残しておきたいローカル変数」というシチュエーションで使うんじゃないでしょうか。

とはいえ

> 「値をずっと残しておきたいローカル変数」

...そんなシチュエーションあるの？


どんなシチュエーション？
====================

みなさんはどのようなシーンで使うかはわかりませんが、
私の場合は、DBや設定ファイルなどに分けている定義データをキャッシュするときに使います。
定義は外に出しておきたいんだけど、毎回取得しにはいきたくないなぁ。。。というときです。

↓VB.Netでいうとこんな感じ

```vbnet

Public Function GetDefiition() As String

  Static def As String = String.Empty

  If String.IsNullOrEmpty(def) Then
    ' なんかDBにとりにいく
    def = fromDB()
    
  End If

  Return def

End Function

```


他に「こんなときに使うよ」というのがあったら教えてください。


JavaScriptとかC#とかでも使いたい！
==============================

基本的には私はC#はVB.Netより優れてると思っているのですが、
このStaticローカル変数、VB.Netにはありますが、C#にはありません。

まぁ、クラス作ってそのメンバ変数にすればそれで事足りるからね。仕方ないね。

でも私はこんだけのことのためにメンバ変数を増やすのは嫌なんです。
「この変数はどこで使ってるのかな？　あぁ、ここでしか使っていないか」
とソースコードを追うたびに確認しなきゃいけないのは苦痛です。

JavaScriptにないのは、そもそもあの言語グローバルスコープと関数スコープの変数しかなかったからね。仕方ないね。


なんとかして実現する
================

はい、クロージャーをつかいます。
クロージャーとはパンとか止める奴のことです(適当)。

C#の場合

```csharp
public static readonly Func<string> GetDefinition = (new Func<Func<string>>(() => 
{
  string def = string.Empty;
  return () => string.IsNullOrEmpty(def) ? def = fromDB() : def;
}))();
```


JavaScriptの場合

```js
const getDefinition = (() => {
  let def;
  return () => def ? def : def = fromDB();
})();
```

できた。


実際問題
=======

どうなんでしょうね。
なんだか、他の言語の機能を無理矢理適用したみたいで、ちょっと気持ち悪くはあるんですが。
唐突にソースコード中にこんな記述がでてきたら「え、なにしてんのこいつ」と思う気もします。

でも私は使っています。

ちなみに
=======

JSでは以下のような書き方をしたこともあります。

```js
function getDefinition() {
  return getDefinition.data ? getDefinition.data : getDefinition.data = fromDB();
}
```

これは、JSでは関数もオブジェクトなので、そのメンバ変数を内部で作ってる、ということですね。
これはこれでなるほどと思えるんですが「動的なメンバ変数」であることと、「外部からもアクセスできてしまう」という欠点があります。
heroku+Node.jsで「Hello World」を作る

## 最初に

最近、Node.jsの勉強を始めました。
herokuでNode.jsを動かす際に学んだことをまとめてみました。

## まず、ローカルで動かす場合

```text:ファイル構成
main.js
```

```js:main.js
var http = require('http'); //httpモジュール呼び出し
var server = http.createServer(function (request, response) {
    // リクエストを受けると以下のレスポンスを送信する
    response.writeHead(200, {'Content-Type': 'text/plain'}); //レスポンスヘッダーに書き込み
    response.write('Hello World\n'); // レスポンスボディに「Hello World」を書き込み
    response.end(); // レスポンス送信を完了する
});
server.listen(8080);  //8080番ポートで待ち受け
```

以下のように省略することも可能です。

```js:main.js
var http = require('http'); //httpモジュール呼び出し
http.createServer(function (request, response) {
    // リクエストを受けると以下のレスポンスを送信する
    response.writeHead(200, {'Content-Type': 'text/plain'}); //レスポンスヘッダーに書き込み
    response.end('Hello World\n'); // レスポンスボディに書き込み＆レスポンス送信を完了する
}).listen(8080);  //8080番ポートで待ち受け
```

ローカルで動かす場合は `main.js` だけあれば動きます。(ちなみにファイル名はなんで良いです。)
コンソール上で以下のコマンドを実行した後で、ブラウザから `http:localhost:8080` へアクセスします。
「Hello World」と画面に表示されれば成功です。

```text:console
$ node main.js
```

## heroku で動かしてみる

herokuで動かす場合は必要なファイルが少し増えます。

```text:ファイル構成
main.js
package.json
Procfile
```

`main.js` の `.listen(8080);` が `.listen(process.env.PORT || 8080);` に変ります。
というのは、herokuは公開ポート番号が一定ではないらしく固定ポートが指定できないためです。
この場合、herokuで実行した際には `process.env.PORT` からポート番号が指定され、ローカルで実行した際には `8080` が指定されます。

```js:main.js
var http = require('http'); //httpモジュール呼び出し
http.createServer(function (request, response) {
    // リクエストを受けると以下のレスポンスを送信する
    response.writeHead(200, {'Content-Type': 'text/plain'}); //レスポンスヘッダーに書き込み
    response.end('Hello World\n'); // レスポンスボディに書き込み＆レスポンス送信を完了する
}).listen(process.env.PORT || 8080); //公開ポートで待ち受け
```

それと `package.json` が必要になります。これが無いとherokuがNode.jsのシステムとして認識してくれないようです。
ファイルさえあれば中身は空でも大丈夫なようですが、一応名前とバージョンはセットしてみました。

```json:package.json
{
  "name": "testapp",
  "version": "0.0.1"
}
```

`Procfile` は自動で実行するコマンドを指定するために必要です。
これを追加しておくと勝手に `node main.js` を実行してくれるみたいです。

```text:Procfile
web: node main.js
```

動かす場合は、上記ファイルをアップロードしてブラウザからherokuサーバーにアクセスします。
「Hello World」と画面に表示されれば成功です。

## 別パターン

`node main.js` の実行は `package.json` でも記載できるらしく、こういう構成でもいけるようです。こっちの方がファイル数は少なくて済みますね。

```text:ファイル構成
main.js (中身は上記パターンと同じ)
package.json
```

```json:package.json
{
  "name": "testapp",
  "version": "0.0.1",
  "scripts": {
    "start": "node main.js"
  }
}
```
scala playframework slick におけるコンテキストスイッチ

# 注意
挙動を試してないので確証はまだないけど、とりあえずの備忘として残した記事です。

# 突然の死
ある日突然リクエストを受け付けるが処理が走らずエラーを返すようになってしまった。

正直なぜそうなったのか分からず、なんやかんやあってスレッドが怪しいのでは？となった。

# スレッドの動き

netty のスレッド -> playframework のスレッド -> slick のスレッド

らしい。

# DBIO の処理

DBIOの処理はこんな感じで書かれていた

```scala
for {
  _ <- DBIO型を返す
  _ <- DBIO型を返す
} yield ()
```

# for は flatMap になる
http://qiita.com/harry0000/items/e37ca3bfb68df839bf55

# slick の flatMap による DBIO合成

https://github.com/slick/slick/blob/04ad92f9280985f1c3692c695b916e0831bed1cc/slick/src/main/scala/slick/dbio/DBIOAction.scala

```scala
  def flatMap[R2, S2 <: NoStream, E2 <: Effect](f: R => DBIOAction[R2, S2, E2])(implicit executor: ExecutionContext): DBIOAction[R2, S2, E with E2] =
FlatMapAction[R2, S2, R, E with E2](this, f, executor)
```

flatMapによる合成は implicit executor: ExecutionContext を要求する

playframework のスレッドで動いていた処理が slick でのDBIOの処理に移る(slickのスレッドに移る)とコンテキストスイッチが発生する。(らしい）

たしかに ExecutionContext を分けているのでそうなのだろう。

flatMapされる毎にコンテキストスイッチが発生。

`play thread -> slick thread`
`play thread <- slick thread`

というような状況になり、ある時


play thread 1 -> slick thread 1 
> slick thread 1に移った時点で play thread は開放されているので別の処理で使われる

play <- slick thread 1
> slick thread 1 の処理が終わった時点で play thread が空いていないと処理を返せないので slick thread 1を握ったまま待つ。

play thread 1 -> slick
> slick thread が空いていないので slick thread が空くのを待つ。

という状況に陥ったのでは無いかという推測。

ちなみに
DBIO.seq とか andThen であれば ExecutionContext を要求しないので同じスレッドで動くのでは？というお話

# しかも
最悪なことに Await.result(しかも Duration.Inf ) されていたため、処理を待ち続けてスレッドを掴み続けていました。

# ていうか
問題発生時にRejectedExecutionException出さないの？
やっぱりよくわからん。
Await.result の Duration.Infで延々と待ち続けるからエラー吐かないとか？

# reactive slick
http://slick.lightbend.com/talks/scaladays2015sf/Reactive_Slick_for_Database_Programming.pdf
[初心者向け]git幼稚園児がgit小学生になるまでに覚えたコマンド（順次更新）

git add, commit, push, pull　しか使えない私が成長していく覚え書きです。

# localのブランチを削除

```
git branch -d ブランチ名
```

localのブランチが増えてきたので整理する時に使うコマンド。
まだmergeされていないbranchは

```
error: The branch 'ブランチ名' is not fully merged.
If you are sure you want to delete it, run 'git branch -D ブランチ名'.
```

とエラーが出る。そんな時は

```
git branch -D ブランチ
```

とすればできた。

# remoteのbranchをlocalに取り込む
まず、remoteのbranchを確認。

```
git branch -r
```

  

```
git checkout -b 好きなbranch名 origin/取り込みたいremoteのbranch名
```

# あるbranchから、別のbranchを作る

```
git branch 別のbranch名(作りたいbranch名) あるbranch名
```

# master以外のbranchから、masterの変更を取り込む

```
git rebase master
```

# localのbranchでmergeする。
まず、git checkoutで取り込む方（本branch）のbranchに移動。その後、取り込まれる方(サブbranch)にgit mergeを実行
```
git checkout (取り込む方のbranch名)
git merge (取り込まれる方のbranch名)
```
Gsonをデシリアライズで使うときのTips

言わずと知れたGsonです。

APIからの返り値(json)をGsonでデシリアライズするさいに、知っておいた方がいいなと思うことを３つご紹介します。

0. 自力でやる方が早い
0. 難読化する方法
0. 受け付ける型を動的に変える

OpenWeatherMapのAPI結果を使ってます。
https://openweathermap.org/

github
https://github.com/kojimamasahiro/GsonTest


# 自力でやる方が早い
Gsonに任せるより、JSONObjectを1つずつ解析した方が処理速度は3割ほど速いです。
可読性や書きやすさがあがりますが、すでに解析するクラスを作成済みの場合は、わざわざGsonにリファクタリングする必要性は少ないかなと思います。
[計測時のソース](https://github.com/kojimamasahiro/GsonTest/blob/1ed6c1800ff1906babb8757eabb5c1e6123177ee/app/src/main/java/sample/kojimamasahiro/gsontest/MainActivity.java)

# 難読化する方法
progurdを使うとGsonがうまくデシリアライズしてくれない場合の対処方法

ジェネリックスで書くとうまくいかないので、

```
Gson gson = new Gson();
gson.fromJson(json, OpenWeatherMapForGson.class);
```

と書くところを

```
Gson gson = new Gson();
gson.fromJson(json, new TypeToken<OpenWeatherMapForGson>(){}.getType());
```
のように書くといいです。

# 返り値の型を動的に変える
二次元配列が空の場合、配列として判定されてしまい、Gsonがうまくデシリアライズしてくれない場合の対処法

自分でデシリアライザーを作る
https://github.com/kojimamasahiro/GsonTest/blob/master/app/src/main/java/sample/kojimamasahiro/gsontest/MainActivity.java#L225

作ったデシリアライザーをGsonに登録する

```
Gson gson = new GsonBuilder()
        .registerTypeAdapter(OpenWeatherMapForGson.class, new OpenWeatherMapForGsonDeserializer())
        .create();
```


# おわりに
昔にGsonを使ったときは衝撃を受けるくらい感動しましたが、解析速度が遅かったり、APIの仕様によっては、自分でデシリアライザーを作らないといけないで、あまりメリットがないような気がしています。
とはいえ、まだDataBindingという裏ボスがいるので、そちらも併せて使うようでしたら、使ってもいいかもしれません。