OmniAICreator/Qiita-1.07M huggingface dataset:
UNITYのBugレポートしてみた

UNITYを使っていて不具合が発生した場合、不具合報告をすると迅速に対応してくれるはずなので
報告の仕方です

基本的に英語なので、私のような英語全くできない人はいつも困りますが
不具合は報告しましょう！！

以下手順をしめします

https://japan.unity3d.com/blog/?p=1878
ここに書いてある内容です

#まずは症状
UNITY 2018.3.0b7 という最新のベータバージョンで新機能のテストを行っていました
負荷の原因がCPU由来なのかGPU由来なのか（CPUバウンド、GPUバウンド）を調べるために
FrameTimingManager.GetCpuTimerFrequency()を呼んだところ
0が返ってきた
ので、調べました

#Reference
https://docs.unity3d.com/ScriptReference/FrameTimingManager.html

> GetCpuTimerFrequency
> This returns the frequency of CPU timer on > the current platform, used to interpret timing results. If the platform does not support returning this value it will return 0.

非対応プラットフォームでは0が返ってくるとのことです
Androidビルドを行い OpenGL、Vulkanと試したが どちらも0でした

それらが対応しているか不明でしたが、Profiling関連はAndroidVulkan　対応しているので
報告することにします

参考
https://docs.unity3d.com/ja/2018.3/Manual/ProfilerGPU.html

ProfilerのGPUプロファイラは Android Vulkanは対応している（ただし こちらも不具合なのか　表示されない・・）

#不具合レポートがないか調べる
まずは　ほかの不具合があがってないか調べます

フォーラム
https://forum.unity.com/forums/android.30/
どこの板にするか悩んだが、Platform/Android にした

issue tracker
https://issuetracker.unity3d.com/

このあたり検索したが それらしい質問がないため　まずはフォーラムで聞いてみる

#フォーラム
https://forum.unity.com/threads/frametimingmanager-getcputimerfrequency-returned-0.575584/

適当な英語というより単語を並べただけだが
Unity Technologies のaleksandrk さんがすぐに回答してくれた。
2018.3 にて Android Vulkanは対応しているはずなのでバグ報告してくれとのこと

#バグ報告
バグ報告をするには、たいてい UNITY Editorから行います
Help->Report Bug　より報告が出来ます
が、できる限りサンプルコードを書いた方がよいのでシンプルなコードを書きます

C#スクリプトを作成し下記のコードをかく

```cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class NewBehaviourScript : MonoBehaviour
{
    // Update is called once per frame
    void Update()
    {
        Debug.Log( FrameTimingManager.GetCpuTimerFrequency() );
    }
}
```

非常にシンプルだ。
そしてレポート画面を出す

プレイヤーでの不具合である
常に出る不具合である
メールアドレス、タイトル、内容を記載し
デフォルトで今のプロジェクトが添付されるので
それを添付して　Reportする

![SnapCrab_NoName_2018-10-31_2-59-52_No-00.png](https://qiita-image-store.s3.amazonaws.com/0/13916/17224fcb-c7b3-eb8a-99f0-20f4f81403d9.png)

#確認メールが来る
しばらくするとメールアドレス宛に 確認メールが来る




~~#念のためUNITY Japanに報告~~
~~念のため レポートしてくれとのことなのでレポートします~~

~~https://unity3d.com/jp/sales/contact-us~~
~~UNITYのお問合せより、メールに書いてある (Case xxxx)タイトル~~
~~を書き　バグレポートしたよって教えます~~

#Issue Tracker
メールにて　現在のステータスの確認できるURLがもらえます

現時点ではまだIssueにはのってませんが　そのうち乗るかもしれません
AWSの基本を勉強してみた

#AWSとは
 AWSとはAmazon Web Servicesの略であり、クラウドコンピューティングサービスです。コンピュータやストレージ、ネットワークが全て仮想的であるため、契約した後に自分で全て設定する必要があります。従来のオンプレミス型のサーバーと異なり、コストが低い、ビジネスの環境変化に迅速に対応できるという点から急速に普及していきました。

#VPCとは
　VPCとはVirtual Private Cloudの略でありネットワークを構成するサービスのことです。仮想ネットワークを作成する際には、IPアドレスの範囲、インターネットゲートウェイを設定する必要があります。
　VPCに割り当てられたIPアドレスの範囲の中からIPアドレスを切り分けてサブネットを作成します。
　また、インターネットをはじめとする外のネットワークと接続するにはインターネットゲートウェイを用いる必要があります。インターネットゲートウェイとはNATのようなものでありプライベートIPアドレスとパブリックIPアドレスを紐づけて変換してくれる仕組みである。

#サブネットとは
　サブネットとはVPCで割り当てられたIPアドレスを切り分けたアドレス空間です。サブネット状にEC2インスタンスなどのサーバーを配置することができます。また、サブネットはアベイラビリティゾーンを跨いで作ることはできません。

#EC2インスタンスとは
　EC2インスタンスとは仮想サーバーであり、AWSにおけるサーバーです。様々なスペックが用意されており、負荷が強くなった時に自動的に性能アップしてくれるT2インスタンスや、アイドル時間とアクティブ時間のCPU性能のさが少ないM4インスタンスなどがあります。インスタンの性能を上げることを **スケールアップ** と言います。

#これからやりたいこと
　現在、AWSを契約してVPC、サブネット、EC2インスタンスの作成を行いCakePHPの環境設定を行いました。しかし、Cakeの環境設定の部分がまだ未完成で解決に時間がかかっているため、解決し次第手始めに、ブログ投稿サイトを作って、その後面白そうなことに挑戦しようと考えています。
新iPad Proのモバイルページが最悪な話

**注意**:⚠️技術的な内容については期待しないでください。また、初投稿なので読みづらいかと思います。ご容赦ください。
## 新iPad Pro発表！！
日本時間2018年10月30日 23:00、ニューヨークで行われたAppleのイベントで新しいiPad Proが発表されましたね！
期待通りのフルディスプレイ、Face ID、磁力でくっつく新しいApple Pencil。何もかもが素晴らしくて速攻買いたくなりました。
## Appleのサイトで詳細を確認しよう！
と思って僕は[AppleのiPad Proのページ](https://www.apple.com/jp/ipad-pro/)に飛びました。もちろんiPhoneで。
(以後iPhoneのSafariでの閲覧を前提に話を進めます)<img width="414" alt="iPad Proのウェブページの縦のスクリーンショット" src="https://qiita-image-store.s3.amazonaws.com/0/180518/071288ab-5e54-c5e3-ddaa-4a6bdb5ed299.png">
**はじめまして！！**

僕はワクワクしながらページをスクロールしました。そして思ったのです。
> ~~あ！こんなところに再生ボタンがある！！~~

発表会をライブで見たのでPVは既に視聴済みでしたが、こっちだと日本語字幕がついているのでもう一度見る事にしました。
>横画面にして、再生ボタンをタップ！

##あれ、、、？
**なんということでしょう。iPhoneを横向きにした途端、Safariがページをリロードし始めたではありませんか！！**
>ページがクラッシュしたのかな、、？

最初はそう思っていました。しかし次の瞬間！そこには全く違う景色が広がっていました、、、![iPad Proのウェブページの横のスクリーンショット](https://qiita-image-store.s3.amazonaws.com/0/180518/0917e024-3a7c-ebab-7943-9f691356b15a.png)
**なんこれ？！しかも縦にスクロールできない！！**

## 何が起こったのか
1. 画面の向きを変える
2. ブラウザの縦横のサイズが変わる
3. JavaScriptでそれを検知
4. 横画面用にページを再構築(レイアウトや画像)

大急ぎで書いたので、ちゃんと調べたりコード読んだりしたわけではありませんが、恐らくこれで合っているでしょう。
リロード後に読み込んでいるURL・HTMLファイルはどちらも同じなので、別のページに飛んだわけではないようです。

## これの何が最悪なのか
画面の向きやサイズによって表示内容やその方法を変えるのは、モバイルデバイス向けのページにはむしろ有効な手段と言えるでしょう。
**しかし**
このページには以下のような問題点があると感じました。

- 切り替えにリロードを伴う。
- やたら横スクロール
- と思いきや縦スクロールも混在

### 切り替えにリロードを伴う
PC版とモバイル版で別々のページを用意しているのであれば全く問題ありませんが、このページはそうではありません。
リロードすることによりユーザーを待たせ、体験を悪化させる上にサーバー、回線、デバイスに余計な負担をかけてしまいます。
さらにこのリロードは先述のように動画再生中でも強制的に発動するため、ますます不適切です。。。

### やたら横スクロール
![iPad Proのウェブページの横のスクリーンショット](https://qiita-image-store.s3.amazonaws.com/0/180518/0917e024-3a7c-ebab-7943-9f691356b15a.png)
スクリーンショットの右の方に、「スワイプ〉」とあります。
「横向きに持ってるんだから横スクロールにしよう！」というクリエイティブな発想が見受けられますが、実際はそんなに良いものではない。ものすごく見づらい、、
加えて、このページの横スクロールはなぜか非常に重く、カクカクとしていました。「僕がiPhone 6s Plus使ってるから重いのか？」とか思ったりもしましたが、そんなはずは、、、
**追記**
iPhone Xでも同様に少しカクツクとのコメントをいただきました。やっぱり性能は関係なさそうですね。

### と思いきや縦スクロール
**参考動画**
[![参考動画](http://img.youtube.com/vi/kS-vQ2fMejw/0.jpg)](http://www.youtube.com/watch?v=kS-vQ2fMejw)

これだけ振り回されて、最終的には裏切られました。
なんと、このページの最後の部分は横にスワイプしてるのに縦にスクロールしだした！！かと言って縦にスワイプしてもスクロールしない、、、

## まとめ
何をしたいのかよくわからないページになってしまっていると感じました。(縦持ちならいつも通り最高なんだけどなぁー、、、)
トップの画像を横向きのiPad Proに置き換えて、レイアウトを少しCSSのメディアクエリでいじるだけの方がよっぽど良いものになった気がしました。
初心者がherokuでrequire_onceしたときに困った話

# どう困ったのか？
本当に初歩的なことだとは思いますがたとえば、下のようなファイル構造になっているとき

- test.php
- testfile
    - hoge.php


```php:test.php
<?php
require_once ("./testfile/hoge.php"); //'testfile'というファイルの'hoge.php'を読み込む

echo $test; //'$test'は'hoge.php'から得る
?>
```

```php:hoge.php
<?php
$test = 'hogehoge'; //'$test'に「hogehoge」を格納する
?>
```

##ローカル環境で'test.php'を実行すると

```console
$ php test.php
//hogehoge
```

このように、正常に読み込まれ実行されます。

##Herokuの環境で実行すると

Herokuの環境で実行してみると**'hoge.php'が読み込まれません**。
ファイルの階層もチェックし、ローカルと同じ状態になっているにも関わらずです。

これが無理なら、**相対パス**でなく**絶対パス**でファイルにアクセスしてみようと試みました。

##相対パスから絶対パスへ
'index.php'につぎのようなプログラムを実行させ、絶対パスを調べました。

```php:index.php
<?php
echo __DIR__;
//「/app/index.php」と出力された
?>
```

これを参考に'test.php'のコードを次のように書き換えました。

```php:after__test.php
require_once ("/app/testfile/hoge.php"); // '.'を削除し、'/app'を先頭に追加

echo $test;
?>
```

##再度、Herokuの環境で実行
書き換えたあと、再びデプロイして実行すると、**読み込まれませんでした。。**
絶対パスが間違えているのかと思い、ファイルの階層構造を念入りに調べましたが、
絶対パスが間違っていないことがわかっただけで読み込むための手掛かりは得られませんでした。

#解決策
ここで、ふと思いつきました。
DIRをそのままrequire_onceの構文に入れてみたら、うまいこといくのでは？と。

```php:test.php
<?php
require_once __DIR__ . ("/testfile/hoge.php") // '/app'を削除し、'__DIR__ .'を追加

echo $test;
?>
```

このように書き換え実行すると、**正常に読み込まれました！**

なぜ、直接絶対パスを書いた場合では読み込まずに、**DIR**をもちいると読み込むのかは初心者の私にはわかりませんでした。
（たぶん、詳しい人がコメントしてくれるのでそれを参考に追記します。）

#結論
**DIR**を積極的に使おう！
DIRを用いれば違う環境で使用するときに、パスの書き換えの必要が（ほとんど）なくなると思います。
そして、今回のように困ることやエラーも減る要因になると思います。

ここまで読んでいただき、ありがとうございました。
JUCEでVSTプラグインを作るときにGUIを実装するのが面倒な時に役立つTips

# はじめに

JUCEは、C++言語によるマルチメディア系アプリケーションの開発を支援するフレームワークです。JUCEはオーディオやMIDIを扱うアプリケーションに特化したAPI群が整備されているため、簡単に楽器アプリケーションを実装することができます。
JUCEにはオーディオプラグインを開発するためのテンプレートが充実しています。VST/AudioUnit/AAX/RTASプラグインといった、DTMで広く使われている主要なオーディオプラグインをビルドすることができます。


# オーディオプラグインを構成するクラス

JUCEでは、プロジェクト作成時に2つのクラスによってオーディオプラグイン（VSTプラグイン）が構成されます。

+ xxxAudioProcessorクラス...オーディオプラグインのインターフェース
+ xxxAudioProcessorEditorクラス...オーディオプラグインのGUIを定義するクラス


# GUIの実装が面倒な時ってありますよね？

下の図は私が実際に作成したプラグイン・シンセサイザーです。パラメーターが20個以上あるので、GUIの実装もそれなりに時間を費やしました。
でも、例えばプロトタイプ段階での開発であったり、特定のアルゴリズムをテストする目的であれば、GUIに凝る必要が無いのが実際の所だと思います。

![SimpleSynth.PNG](https://qiita-image-store.s3.amazonaws.com/0/93566/abc055a0-90a7-1657-4a14-87f64b21d51f.png)


# 汎用的なGUIを表示する機能を利用する

JUCEライブラリには、汎用的なGUIを生成してくれるGenericAudioProcessorEditorクラスが提供されています。以下に、その使い方を簡単に示します。
※APIリファレンス https://docs.juce.com/master/classGenericAudioProcessorEditor.html


### パラメータを追加する

プロセッサー側のクラス（xxxAudioProcessorクラス）にパラメータを追加する処理を実装します。

```


// コンストラクタ
xxxAudioProcessor::xxxAudioProcessor()
#ifndef JucePlugin_PreferredChannelConfigurations
     : AudioProcessor (BusesProperties()
                     #if ! JucePlugin_IsMidiEffect
                      #if ! JucePlugin_IsSynth
                       .withInput  ("Input",  AudioChannelSet::stereo(), true)
                      #endif
                       .withOutput ("Output", AudioChannelSet::stereo(), true)
                     #endif
                       )
#endif
{
	AudioParameterFloat* parameter1 = new AudioParameterFloat("PARAMETER_1", "PARAMETER_1", -36.f, 6.f, -3.0f);
	AudioParameterInt* parameter2 = new AudioParameterInt("PARAMETER_2", "PARAMETER_2", 1, 128, 8);
	AudioParameterBool* parameter3 = new AudioParameterBool("PARAMETER_3", "PARAMETER_3", true);

	addParameter(parameter1);
	addParameter(parameter2);
	addParameter(parameter3);
}

```

### xxxAudioProcessor::createEditor関数の返り値を変更する

```
AudioProcessorEditor* xxxAudioProcessor::createEditor()
{
    return new xxxAudioProcessorEditor (*this);
}
```

↓ GenericAudioProcessorEditorクラスのインスタンスを返すように変更する

```
AudioProcessorEditor* xxxAudioProcessor::createEditor()
{
    return new GenericAudioProcessorEditor(this);
}
```

### GUIにパラメータ操作用のコンポーネントが自動で配置される

上記の実装を加えてビルドすると、このように、GUIにパラメータ操作用のコンポーネントが自動で配置されます。
![Generic.PNG](https://qiita-image-store.s3.amazonaws.com/0/93566/3621ac43-ebe9-9a05-6365-c7043c806afc.png)
[bootstrap]display設定で画面サイズに応じて表示切替

[プログラミング教室ITWORKS](http://listenmaker.1strentalserver.info/itworks/)のayakaです。

自身の作成しているホームページにレスポンシブデザイン対応するためにBootstrapを利用してみました。
流石に幅広く使われるだけあって使いやすいですね。
[Bootstrap](https://getbootstrap.com/)のドキュメントやサンプルもわかりやすいです。
ドキュメントからは若干分かりずらかったdisplay設定を下記にまとめます:slight_smile:

#Bootstrapのコンポーネントの基本動作
基本的にBootstrapで用意されているComponentはブラウザの画面サイズに応じてリサイズされます。（Navbarは画面サイズに応じて短縮表示）したがって既存のdivやtableにBootstrapのclassを適用するとそれだけでレスポンシブに動いてくれます:open_mouth:

```html:index.html
<div class="container"> -既存コンテンツ- </div>
```
#画面サイズに応じて表示/非表示を簡単設定
PCの画面サイズでは＜コンテンツＡ＞を表示させたいがスマートフォンの画面サイズでは＜コンテンツＢ＞を表示させたい場合下記のように記述し表示設定を指定することが可能です。

```html:index.html
<div class="d-none d-lg-block">
       コンテンツＡ
</div>
<div class="d-block d-lg-none">
       コンテンツＢ
</div>
```
classにBootstrapで用意されているCSSを設定すれば簡単に
画面サイズに対する表示設定を行うことができます。

**d-(画面サイズ指定)-表示設定**

- 画面サイズ指定
    - 省略(xs)
    - sm
    - md
    - lg
    - xl

- 表示設定
    - none：非表示
    - inline：インライン表示
    - block：ブロック表示
    
---
参考
[Bootstrap](https://getbootstrap.com/)
[Bootstrap4移行ガイド](https://cccabinet.jpn.org/bootstrap4/)
自分メモ_AWS_VPC

■やってみたこと
パワポ見てばかりじゃだめだ、手を動かせという記事に触発されて手を動かす。
NW屋なので、なじみありそうなVPCにチャレンジだ。
AWS上にVPCを設定して自宅からPING応答を確かめられればいいかな。
東京と他リージョンでレイテンシの違いが見えたら面白いかも。
　→実践！！

■手を動かしてみて学べたこと
・サブネットは最小/28
　→ping受けられればいいかなと/32を想定していた

・IGWへのPING非推奨（出来ない？監視用の定期ping不可？）
　→pingの受け先としてEC2を建てる前提と理解

■疑問
・AWS構築はCLIとGUIどっちが主流なんだろうか。
・構築後のコード化は大前提？

■次回やりたいこと
EC2を建てて自宅からping応答を確かめる
東京リージョンとサンパウロリージョンのレイテンシの違いを確かめる
ONNX

https://qiita.com/AtuNuka/items/905dddfc62ba32357aa1

https://qiita.com/mitmul/items/6a0c62be29b27b6b3fbe

https://github.com/onnx/onnx

https://www.google.co.jp/amp/s/www.kumilog.net/entry/pytorch-onnx%3famp=1

http://proc-cpuinfo.fixstars.com/2018/04/onnx-trial/

https://github.com/pfnet-research/menoh
[Django] フォームのフィールドを動的に生成する

stack overflow で[質問してた件](https://ja.stackoverflow.com/questions/49796/django%E3%81%AE%E3%83%95%E3%82%A9%E3%83%BC%E3%83%A0%E3%82%92%E4%BB%BB%E6%84%8F%E5%80%8B%E6%95%B0%E7%94%9F%E6%88%90%E3%81%99%E3%82%8B%E6%96%B9%E6%B3%95/49807#49807)が自己解決したのでQiitaに残して備忘録にしようと思い投稿しました．
初投稿なので温かい目で見てもらえればと思います．
#目的
**ユーザーが指定した個数の入力フォームがほしい！**
つまり動的にフィールドを追加してやりたかったわけです．
まあHTMLを直接追加してやれば出来るんですが，Djangoを使う以上でFormクラスでちゃんと管理してやりたいわけです．

ここに書いてある以外でもっといい書き方知ってたらコメントで教えてください．
#Formクラスの仕様
まずDjangoのFormクラスの仕様について自分の理解しているところをちょろっと書きます．
##フォームの基本的な使い方

```python:forms.py
from django import forms

class TestForm(forms.Form):
    hoge = forms.CharField(label="hoge")
    fuga = forms.CharField(label="fuga")
```
上のコードで作ったTestFormを作って，例えば```form```とかいう名前でテンプレートに投げてやれば```{{ form.as_p }}```とか```{{ form.as_table }}```とかでinputフォームが出てくる．(この辺はDjangoの公式? [Documentation](https://docs.djangoproject.com/en/2.1/) の[ここ](https://docs.djangoproject.com/en/2.1/topics/forms/#s-form-rendering-options)とか別記事を参照．)
特にフォームをバラバラの位置に出したいときなど，個別にフォームを指定したいときは，```{{ form.hoge }}```のように指定します．
##問題点：変数名=フィールド名
さて，今一度```forms.py```のコードを見てもらうと，クラス直下で定義した変数名がそのままフィールド名になっていることが分かります． ```django.forms``` を見てみるとどうもFormクラスはBaseFormというクラスを継承しているのですが，その際にメタクラスを使ったりして(この辺はよく理解していません)変数名をキー，定義したフィールドを値にしてfieldsという辞書型配列に格納しているようです．ですので```forms.py``` で書いたクラスに配列で変数を定義したりしてもダメっぽいんですね．

#対策
配列を入れるとその配列の要素を名前とするフィールドをもつFormクラスを返してくれるような関数を作りました．

```python:forms.py
from django import forms

def create_form(myary, *arg):
    f = forms.Form(*arg)
    for val in myary:
        f.fields[val] = forms.CharField(label=val)
    return f
```
こんな感じで行けました！

```views``` はこんな感じ

```python:views.py
class FormView(TemplateView):
    def __init__(self):
        self.keys = range(5)
        self.params = {
            'form':test(self.keys),
        }
    def get(self, request):
        return render(request, 'temlate.html', self.params)
    def post(self, request):
        self.params['form'] = test(self.keys, request.POST)
        return render(request, 'template.html', self.params)
```

ここでは```range(5)```を渡してやってます．POSTのときにはrequest.POSTを一緒に投げてやる．
#改善点
引数のとこなんかは辞書型にしてやったり，labelとかバリデーションなんかの設定も投げれる様にすればよさげ

書いてて気づいたんですけど，たしかJSONでFormクラス作れたような．．．
ReactNativeでのiOSプッシュ通知の実装方法

React Nativeでプッシュ通知機能追加方法を紹介します。

## ライブラリ
プッシュ通知を実装するために、react-native-push-notificationを使います。
[zo0r/react-native-push-notification: React Native Local and Remote Notifications] (https://github.com/zo0r/react-native-push-notification)
このライブラリはiOS・Android両方対応してますが、今回はiOSのみ設定します。

### インストール
初めに、ライブラリをインストールします。

```
 yarn add react-native-push-notification
```

### リンク
利用するためには、手動でリンクさせる必要があります。
[Linking Libraries · React Native](https://facebook.github.io/react-native/docs/linking-libraries-ios#manual-linking) を参考にリンクさせます。

## 実装
プッシュ通知の設定をします。

```App.js
 import { PushNotificationIOS } from 'react-native';
 import PushNotification from 'react-native-push-notification';
 
 PushNotification.configure({
   // (optional) Called when Token is generated (iOS and Android)
   onRegister(token) {
     console.log('TOKEN:', token);
   },
 
   // (required) Called when a remote or local notification is opened or received
   onNotification(notification) {
     console.log('NOTIFICATION:', notification);
 
     // process the notification
 
     // required on iOS only (see fetchCompletionHandler docs: https://facebook.github.io/react-native/docs/pushnotificationios.html)
     notification.finish(PushNotificationIOS.FetchResult.NoData);
   },
 
   // ANDROID ONLY: GCM or FCM Sender ID (product_number) (optional - not required for local notifications, but is need to receive remote push notifications)
   // senderID: 'YOUR GCM (OR FCM) SENDER ID',
 
   // IOS ONLY (optional): default: all - Permissions to register.
   permissions: {
     alert: true,
     badge: true,
     sound: true,
   },
 
   // Should the initial notification be popped automatically
   // default: true
   popInitialNotification: true,
 
   /**
    * (optional) default: true
    * - Specified if permissions (ios) and token (android and ios) will requested or not,
    * - if not, you must call PushNotificationsHandler.requestPermissions() later
    */
   requestPermissions: true,
 });
```

ローカル通知を利用して、プッシュ通知を表示させます。

```App.js
 export default class App extends Component<Props> {
   render() {
     const handleOnPress = () => {
       PushNotification.localNotificationSchedule({
         message: 'これはテストの通知です。アプリ起動後10秒後に配信されます',
         date: new Date(Date.now() + 10 * 1000),
       });
     };
 
     return (
       <View style={styles.container}>
         <Text>プッシュ通知を表示させるためにボタンを押してください</Text>
         <Button title="クリック" onPress={handleOnPress} />
       </View>
     );
   }
 }
```

localNotificationScheduleを利用し10秒後に表示させています。
iOSだとアプリを開いた状態だと、通知されません。プッシュ通知を確認するには、アプリを閉じている状態でなければいけません。

- ボタンをクリック
- アプリを閉じる
- 10秒待つ

ことで、上記のコードでプッシュ通知の動作確認をすることができます。

## 参考
- https://github.com/zo0r/react-native-push-notification/issues/619#issuecomment-375030928
- [How To Implement Push Notifications for iOS and Android In React Native] (https://apiko.com/blog/react-native-push-notifications/)
デフォルトキューブをz方向に1動かす (Python for Blender クックブック)

# デフォルトキューブをz方向に1動かす
Pythonを使ってBlenderでできる事をまとめています。解説もあります。
[はじめに](https://qiita.com/KTakahiro1729/items/5de5f60982af37d23aa0)
[レシピ一覧](https://qiita.com/KTakahiro1729/items/57f4e1f5495c5e54d431)

Pythonの難易度: ★☆☆☆☆

## サンプルコード

例1

```python
import bpy
obj = bpy.data.objects["Cube"]
obj.location.z = obj.location.z + 1
```

例2(Pythonの難易度: ★★★☆☆)

```python
import bpy, mathutils
obj = bpy.data.objects["Cube"]
obj.location += mathutils.Vector((0,0,1))
```

上記サンプルコードを、Blender内蔵のテキストエディタに貼り付けた後、<kbd>Alt</kbd>-<kbd>P</kbd>を実行してください。

その他、`bpy.ops.transform.tranlate`を使う方法もあります。
## 解説

### bpy.data.objects["Cube"]
PythonからBlenderを使うには`bpy`というライブラリを使います。
例えば、`bpy.data`にはBlender内の様々な変数（オブジェクトのインスタンス）が格納されています。

例えば、オブジェクト一覧は`bpy.data.objects`から、マテリアル一覧は`bpy.data.materials`からアクセスできます。
この一覧の型は`bpy.types.bpy_collections`であり、この型は辞書とリストを合わせたようなものです。[^1]
[^1]: bpy.data.objectsの型が`bpy_collections`と説明しましたし、typeやisinstanceを使ってもその通りですが、実際には`bpy.types.BlendDataObjects`です。この辺りはどうやってるんだろう……

今回は`Cube`という名のオブジェクトにアクセスします。

### obj.location
`obj.location`は3次元ベクトルで、オブジェクトの位置を表します。
これのz座標を使うには`.z`を使ってください。


### mathutils.Vector
PythonからBlenderを使うには基本的に`bpy`を使いますが、それ以外にもいくつかのライブラリがあります。
例えば、`bmesh`はメッシュを扱うための、`mathutils`は数学を扱うためのライブラリです。

`mathutils.Vector`はベクトルを扱うためのクラスであり、クラスのコンストラクタです。
したがって、`mathutils.Vector((0,0,1))`というのは`(0,0,1)`のベクトルを指します。

これらのベクトルは足し算が可能です。
Elixirの単独キー関数をサクッと複数キー対応する

[fukuoka.ex](https://fukuokaex.connpass.com/)代表のpiacereです
今回もご覧いただいて、ありがとうございます:bow:

Elixirで関数を書いていると、Enum.drop()のような、複数キーが指定可能な処理をサクっと書きたいシチュエーションがあります

単独キーの関数を、複数キー対応することで、このコツのようなものをシェアしたいと思います

# 関数サンプル：マップリストを単独キー指定で文字列置換

マップリストのマップにある値を、単独キー指定で文字列置換する関数を以下のように書いてみます

```elixir
defmodule MapList do
	@doc """
	Replace map value

	## Examples
		iex> MapList.replace( [ %{ "c1" => "v1", "c2" => "v2" }, %{ "c1" => "v3", "c2" => "v4" } ], "c1", "v", "Value" )
		[ %{ "c1" => "Value1", "c2" => "v2" }, %{ "c1" => "Value3", "c2" => "v4" } ]
	"""
	def replace( map_list, column, pattern, replacement ) do
		map_list |> Enum.map( fn item_map -> Map.put( item_map, column, String.replace( item_map[ column ], pattern, replacement ) ) end )
	end
end
```

# マップリストを複数キー指定で文字列置換

上記関数を複数キー対応すると、以下のようになります

```elixir
defmodule MapList do
	@doc """
	Replace map values

	## Examples
		iex> MapList.replace( [ %{ "c1" => "v1", "c2" => "v2" }, %{ "c1" => "v3", "c2" => "v4" } ], [ "c1" ], "v", "Value" )
		[ %{ "c1" => "Value1", "c2" => "v2" }, %{ "c1" => "Value3", "c2" => "v4" } ]
		iex> MapList.replace( [ %{ "c1" => "v1", "c2" => "v2" }, %{ "c1" => "v3", "c2" => "v4" } ], [ "c1", "c2" ], "v", "Value" )
		[ %{ "c1" => "Value1", "c2" => "Value2" }, %{ "c1" => "Value3", "c2" => "Value4" } ]
	"""
	def replace( map_list, columns, pattern, replacement ) do
		columns
		|> Enum.reduce( map_list, fn column, acc -> 
			acc |> Enum.map( fn item_map -> Map.put( item_map, column, String.replace( item_map[ column ], pattern, replacement ) ) end )
		end )
	end
end
```

ポイントは、以下5点です

- 第2引数を、複数キー指定可能とするため、リストに変更した
- 複数キーでEnum.reduce()を回すことで、キーの個数分、処理を繰り返すようにした
- Enum.reduce()の初期値をmap_listとし、それをaccとして、各キーの更新を反映させた
- マップ内で行う置換処理は、変更前と変えていない（パイプの前がmap_listからaccに変わっただけ）
- 複数キーのテストケースを追加した　※実際はTDDしているので、先にテストから変更した

「Enum.reduce()がちょっと慣れなくて苦手」という方は、「accの初期値はmap_list」という点と、「accが繰り返し更新される」という点に着目すると、少し読みやすくなるかも知れません

# p.s.「いいね」よろしくお願いします

ページ左上の ![image.png](https://qiita-image-store.s3.amazonaws.com/0/155423/4d515047-cc48-382e-c2b1-3ad0cc50dbbf.png) や ![image.png](https://qiita-image-store.s3.amazonaws.com/0/155423/a4e3da58-70a3-4197-95a2-6a6906650d01.png) のクリックを、どうぞよろしくお願いします:bow:
ここの数字が増えると、書き手としては「ウケている」という感覚が得られ、連載を更に進化させていくモチベーションになりますので、もっとElixirネタを見たいというあなた、私達と一緒に盛り上げてください！:tada:
Aurora、クラスタ構成でホスト名にアクセスした時、ping 打つ毎にIPアドレスが変わるのを確認する


↓のクラスタ構成の時に、
![image.png](https://qiita-image-store.s3.amazonaws.com/0/299475/a3543393-9026-8dad-9d29-cc2747f0eaa8.png)

エンドポイントが↓になってて、
![image.png](https://qiita-image-store.s3.amazonaws.com/0/299475/75922b68-8358-9cfa-e315-ff7b3be2d923.png)


読み込みエンドポイントにping打つと、pingのタイミングによってIPアドレスが変わってる確認。

```
[ec2-user@ip-172-31-37-104 ~]$ ping mydbinstance-cluster-1.cluster-ro-c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com
PING mydbinstance2.c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com (172.31.10.31) 56(84) bytes of data.

[ec2-user@ip-172-31-37-104 ~]$ ping mydbinstance-cluster-1.cluster-ro-c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com
PING mydbinstance3.c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com (172.31.31.214) 56(84) bytes of data.

[ec2-user@ip-172-31-37-104 ~]$ ping mydbinstance-cluster-1.cluster-ro-c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com
PING mydbinstance3.c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com (172.31.31.214) 56(84) bytes of data.

[ec2-user@ip-172-31-37-104 ~]$ ping mydbinstance-cluster-1.cluster-ro-c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com
PING mydbinstance2.c32g4nbcrsih.ap-northeast-1.rds.amazonaws.com (172.31.10.31) 56(84) bytes of data.
```

※クラスターエンドポイントの方には何回ping打っても同じIPアドレス

#### 備考

故にコネクションプール張りっぱなしにして大丈夫です？っていう話につながる。
※最初に取得したIPアドレスにつなぎっぱなしにして良いのか問題
Pythonで記事をスクレイピングしてCSVに落そう

##はじめに

前回書いた、
[画像をスクレイピングして保存までをPythonでやってみた[初心者向け]](https://qiita.com/tatsuo-iriyama/items/20de9101aa73f30e1a40)
の記事を通して、スクレイピングを理解した訳ですが、今度はCSVに落とすまでを行ってみました。

今回のスクレイピングもPythonを使用して行いました。
Seleniumという自動でブラウザを操作してくれるライブラリを使用してスクレイピングを行いました。

Seleniumがどういうライブラリなのかわからない方はこちらを参考にしてみて下さい。
[参考]
https://techacademy.jp/magazine/18690


##スクレイピング


```python:sample.py
from selenium import webdriver
import pandas as pd

browser = webdriver.PhantomJS()
url = '対象ページのURL'
browser.get(url)
df = pd.DataFrame({'title':[], 'date':[], 'like':[]})

while True:
    if len(browser.find_elements_by_class_name('要素')) > 0:
        posts = browser.find_elements_by_class_name('要素')
        for post in posts:
            title = post.find_element_by_css_selector('要素').text
            date = post.find_element_by_css_selector('要素').text
           like = post.find_element_by_css_selector('要素').text
            series = pd.Series([title, date, like],['title', 'date', 'bookmarks'])
            print(series)
            df = df.append(series, ignore_index=True)

        link = browser.find_element_by_link_text("要素")
        link.click()
        browser.implicitly_wait(10)
    else:
        break

df['like'] = pd.to_numeric(df['like'].str.replace('users', ''))
df = df.sort_values(['like'], ascending=False).reset_index(drop=True)
df.to_csv('hoge.csv')
print('完了')
```

Webサイトの検索結果などで複数の記事が存在する場合を想定して書いたコードになります。

`DataFrame`では、欲しいデータの種類だけ追加します。
今回の場合、私は記事のタイトルと、投稿日、良いね数、が欲しかったので、3つにしています。

find_element_by_〇〇では、Googleのデベロッパーツールを使用して、取得要素を選定しました。

pandasでソートをした事が無かったので、下記の記事は参考になりました。
ソートする値が、`文字列なのか`、`数値なのか`が大切です。
[参考]
https://qiita.com/y_sk71/items/c22f47bd4ddc1dc46dc8

find_element_by_〇〇に関してはこちらが参考になりました。
`element`と`elements`で異なるので注意です。
[参考]
https://kurozumi.github.io/selenium-python/locating-elements.html


##まとめ

スクレイピングは、色々なシチュエーションで役立つし、覚えて置いて損は無い技術である事は間違い無いと思います。難しくはないので、やった事がない方は、ぜひ挑戦してみて下さい。

##おまけ
Twitterやってます！外部のエンジニアの方ともどんどん繋がりたいと考えていますので、是非フォローして頂ければと思います！[@Tatsuo96](https://twitter.com/Tatsuo96)
p.s.今年の2月までは溶接職人でした。ガッツ系エンジニアとしてやらせて頂いております。
エクセルで横に並んだ複数デーブルを一つの縦に並んだテーブルに変換するマクロ(VBA)書いてみた

依頼を受けたので、VBAほぼ書いたことないですが、グーグル先生の力を借りて書いてみました。

作成したxlsmファイルは[こちら](https://github.com/LittleWat/vba/blob/master/shrink_column/shrink_column.xlsm)

やりたいことは下記のように、一つのシートに週単位（下記だと２カラム１セット）などでテーブルがあるときに、
<img width="1440" alt="before.png" src="https://qiita-image-store.s3.amazonaws.com/0/104256/106fd4fb-46a5-24d1-68eb-ea74a84702ea.png">

下記のように一つの長いテーブルにまとめたい。
<img width="1440" alt="after.png" src="https://qiita-image-store.s3.amazonaws.com/0/104256/2f5962d8-4c76-a2c9-32b3-ae2f14255605.png">

下記のようなコードでできますた。（ツッコミどころ満載かもしれませんが参考まで。）

```vb:shrink_column.vb
Sub shrink_colums()
    ' ---------- 要設定ゾーン Start ----------
    NUM_COL_SET = 2  ' ２列１セット
    HEADER_OFFSET = 1  ' ヘッダ行の行数
    FROM_SHEET_NAME = "Sheet1"  ' コピー元のシート名
    TO_SHEET_NAME = "ColumnShrinked"  ' コピー先のシート名
    ' ---------- 要設定ゾーン End ----------

    Worksheets.Add after:=Worksheets(Worksheets.Count)
    ActiveSheet.Name = TO_SHEET_NAME

    Worksheets(FROM_SHEET_NAME).Activate
    num_col = Cells(HEADER_OFFSET, 1).End(xlToRight).Column

    Worksheets(FROM_SHEET_NAME).Range(Cells(HEADER_OFFSET,1), Cells(HEADER_OFFSET, NUM_COL_SET)).Copy Worksheets(TO_SHEET_NAME).Cells(HEADER_OFFSET, 1)

    current_bottom_row = HEADER_OFFSET
    Dim x As Integer
    For x = 1 To num_col Step NUM_COL_SET
        num_row = Cells(HEADER_OFFSET+1, x).End(xlDown).Row - HEADER_OFFSET

        Worksheets(FROM_SHEET_NAME).Range(Cells(HEADER_OFFSET+1, x), Cells(HEADER_OFFSET+num_row, x+NUM_COL_SET-1)).Copy Worksheets(TO_SHEET_NAME).Cells(current_bottom_row+1, 1)
        current_bottom_row = current_bottom_row + num_row
    Next x

    MsgBox "Finished!!! Result Sheet Name is " &  TO_SHEET_NAME
    Worksheets(TO_SHEET_NAME).Activate
End Sub
```

macのエクセルを使っているが、エディタが強くない。atomでpluginいれて書きますた。やっぱりatom使いやすい。
【Rails】Devese gem のヘルパーメソッドを使ってログイン状態を検証する 

RailsTutorialを一通りした後Deviseを導入したアプリを作ることになったので
その時、便利に感じたこと、よく使うなと感じたことをまとめておこうと思います。
ちなみに全てのDeviseの機能を使用しているわけではないです。

#動作環境
ruby ,  2.5.1
rails , 5.1.6
Devise , 4.4

#下記公式のGithubページ
https://github.com/plataformatec/devise

#Deviseとは
deviseはログイン認証機能を提供するgemです。
rails generate ~ するだけでログイン・ログアウト、新規ユーザの作成、削除、バリデーション等
昨今の　Webサイトであるようなログイン機能をすばやく実装できます。

#Deviseで使えるようになるヘルパーメソッド
Deviseで生成されたControllerとViewの内部で以下のメソッドが使えるようになります。

| メソッド | 機能 |
|:--|:--|
| before_action :authenticate_user! | ログイン済ユーザーのみにアクセスを許可 |　
| user_signed_in? | ユーザーがサインイン済かどうかを判定する |
| current_user | サインインしているユーザーを取得 |
| user_session | ユーザーのセッション情報にアクセスする |

※モデル名がUser以外の場合、「user」部分を書き換える必要があります。

#before_action :authenticate_user! の使い方
ログイン済でないとアクセスして欲しくないアクションに設定します。
デフォルトでログインしていない場合はログイン画面に遷移する仕様になっていますので
カスタマイズしたい場合はコントローラのリダイレクトを上書きしなければなりません。

```ruby
class SampleController < ApplicationController
  before_action :authenticate_user!, only: [:show]

  def index
  end

  def show
  end
end
```

#user_signed_in?の使い方
View等でログイン済みのユーザにのみ表示させる等特定のユーザ毎に表示させるオブジェクトを分けたい時に使えます。
例ではログイン済みの場合のみログアウトボタンが表示されます。

```erb
<%= link_to "ログアウト", destroy_user_session_path, class: "btn" if user_signed_in? %>
```

#current_userの使い方
サインインしているユーザーとそのIDを取得して
例ではプロフィールをクリックすると、サインインしているユーザ個別のページを表示させるようなことができます。


```erb
<%= link_to "プロフィール", user_path(current_user.id) %>
```

※user_sessionについては私は使用したことがないです。

#RSpecでDeviseのヘルパーメソッドを使かってみる
sign_in、sign_outのメソッドを使うことでユーザのログイン、ログアウトの状態を変更することできます。
まずは、rails_helperにDeviseのテストヘルパーをロードさせます。

```ruby:rails_helper.rb
RSpec.configure do |config|
  # Remove this line if you're not using ActiveRecord or ActiveRecord fixtures
  config.fixture_path = "#{::Rails.root}/spec/fixtures"

#
# Rspec既存のコード
#

#Deviseのテストヘルパーを読み込ませる
config.include Devise::TestHelpers, :type => :controller
```

例ではControllerテストに記述。

```ruby:sample_controller_spec.rb
require 'rails_helper'

RSpec.describe SamplesController, type: :controller do
  describe "#show" do
    #ユーザを生成
    before do
      user = FactoryBot.create(:user)
    #作ったユーザでログイン
      sidn_in user
    end
    # 正常にレスポンスを返すこと
    it "responds successfully" do
      get :show, params: {id: user.id}
      expect(response).to be_successful
    end
  end
end
```
#初めて使ってみた感想
「なんかよくわからんけど、ログイン機能ができてる」みたいな印象。
そのため初心者からだと公式ドキュメント読んで仕様を理解するのが大変だと思います。
Deviseは便利ですが、こればっか使ってるとセッションや暗号化のやり方を忘れるので
[Ruby on Rails Tutorial](https://railstutorial.jp/)なんかで復習しないとなと思いました。
pythonでXORプチ暗号化

# はじめに

pythonで暗号化をしたくて調べたらpycryptoを利用する記事がいくつかヒットしました。

 [Pythonで暗号化と復号化](https://qiita.com/teitei_tk/items/0b8bae99a8700452b718)

pycryptoは、パディングとか考慮しないといけないみたいですが、便利なラッパークラスが公開されているようですね。
ですが、ユーザー配布するときに、インストールするパッケージが増えるのが嫌だったので単純なXORによる暗号化を実装してみました。

## 用途

個人的には以下の条件の場合は、簡単な暗号でもよいと思っています。（異論は認めます）

  - ローカル利用のみの場合

  　自分の環境のみ利用して、他の人に見られることがないのであれば、情報漏洩のリスクが低いと判断していいと思います。念のために暗号化しておくパターン。

  - スクリプト自体を配布する場合

    スクリプトを見たり、print文を入れればすぐにハックされてしまう場合は、あまり暗号化方式は重要でないと思います。他の問題を優先するべきパターン。

データを送受信する場合や、他人とデータを共有する場合、サーバーで動作するスクリプトの場合はちゃんとAESなどで暗号化したほうがいいと思います。

## XOR

簡単な暗号化といえばXORを利用したものが一般的と思います。
XORの暗号化で調べてみたら[ここ](https://code.i-harness.com/ja/q/139b0af)のような記事がありましたが、
ちょっと使いにくいので、もう少し汎用化してみました。

パスワードのようなテキストを設定ファイルに格納することを想定しているので、テキストと暗号化文字列を相互変換できる機能のみ実装します。
バイナリデータは対応していませんが、ちょっと修正すれば対応できると思います。

## ソース

```python

# 暗号化：引数の２つの文字列をXORした結果をhex文字列で返す
# src_text=暗号化したい文字列
# key=暗号化するためのキー文字列
def crypto_text_to_hex(src_text, key):
    if src_text and key:
        xor_code = key
        # keyが短い場合は、繰り返して必要バイト数を準備する
        while len(src_text) > len(xor_code):
            xor_code += key
        return "".join([chr(ord(data) ^ ord(code))
                        for (data, code) in zip(src_text, xor_code)]).encode().hex()

# 複号：引数のHex文字列とkeyをXORして戻した文字列で返す
# hex_text=暗号化されているhex文字列
# key=複号するためのキー文字列
def decrypto_hex_to_text(hex_text, key):
    if hex_text and key:
        try:
            crypt_data = bytes.fromhex(hex_text).decode()
        except ValueError:
            crypt_data = None

        if crypt_data:
            xor_code = key
            # keyが短い場合は、繰り返して必要バイト数を準備する
            while len(crypt_data) > len(xor_code):
                xor_code += key
            return "".join([chr(ord(data) ^ ord(code))
                            for (data, code) in zip(crypt_data, xor_code)])

```

## 実行

```python
key = "1234567890"
src_text = "crypto test string"
print("src:" + src_text)

hex_text = crypto_text_to_hex(src_text, key)
print("enc:" + hex_text)

decode_text = decrypto_hex_to_text(hex_text, key)
print("dec:" + decode_text)

if src_text == decode_text:
    print("decode OK.")
```

## 実行結果

```
src:crypto test string
enc:52404a444159174c5c4345124040475f595f
dec:crypto test string
decode OK.
```

# まとめ

なんでもAESにすればいいというものでもないと思う。適材適所です。
知らないうちにJSON5 in Babel

JSONは身近なフォーマットですが、手で書こうとすれば案外に書きにくいものです。実は、そういった問題をクリアするような「JSON5」というフォーマットがあって、しかも多くの人が利用可能な環境にあったりもします。

## JSONの書きにくさ

JSONはJavaScriptのオブジェクトリテラルから派生したものですが、データ交換用のフォーマットという性格もあってか、JavaScriptと比べて制約もあります。

* オブジェクトのキーは二重引用符で括る必要がある（一重引用符や、何も書かないのは禁止）
* 文字列も二重引用符で括る必要がある（一重引用符は禁止）
* ケツカンマ禁止
* コメントは入れられない

うっかりしていてJSONとしてInvalidなものを作ってしまうことも多いし、設定ファイルにコメントを付けられないのもストレスの一因になったりします。

## 拡張した、JSON5

そんなJSONの使いにくさへの解決策として、ES5.1のオブジェクトリテラルに沿ってJSONを拡張したものが[JSON5](https://json5.org/)です。JSON5では、以下のような拡張が入っています。

* オブジェクト
  * キーは一重引用符でも、識別子として使えるものならOK
  * ケツカンマOK
* 配列
  * ケツカンマOK
* 文字列
  * 一重引用符もOK
  * 文字列の途中で（バックスラッシュでエスケープすれば）改行OK
  * `\x0f`のようなエスケープシーケンスを使える
* 数値
  * `0xabcd`のような16進法でもOK
  * `16.`や`.23`のような、小数点前後の片方だけ書くのもOK
  * `+12`のようなプラス記号も使える
  * `Infinity`や`NaN`も値として受け付ける 
* コメント
  * `/* ... */`あるいは`// (このあと行末まで) `といったコメントを使える
 
なお、文法は純粋に拡張なので、通常のJSONを書いても、JSON5パーサーで問題なく処理可能です。

```:サイトにあった例を引用
{
  /*
    注： JSON5のシンタックスハイライトがないことと、
    JSONでかけるとInvalidになってしまうので、あえて指定なしにしています。
  */
  unquoted: 'and you can quote me on that',
  singleQuotes: 'I can use "double quotes" here',
  lineBreaks: "Look, Mom! \
No \\n's!",
  hexadecimal: 0xdecaf,
  leadingDecimalPoint: .8675309, andTrailing: 8675309.,
  positiveSign: +1,
  trailingComma: 'in objects', andIn: ['arrays',],
  "backwardsCompatible": "with JSON",
}
```

## 身近にあった実用例

ふつうのJSONであれば、JavaScriptに`JSON.parse`が組み込まれていますので、何も用意しなくても処理できます。一方で、（`eval`という禁断の技を使うのでなければ）JSON5のパーサーは標準で存在しないので、[npmから入れる](https://www.npmjs.com/package/json5)必要があります。

…ただ、多くの人の`node_modules`に、すでに`json5`は存在しているかと思います。実は、[babelが`json5`に依存している](https://www.npmjs.com/package/@babel/core?activeTab=dependencies)のです。

`.babelrc`などはJSONで書く、と考えている人が多いかと思いますが、実はそうではなくて[JSON5として解釈されています](https://babeljs.io/docs/en/config-files#json5)。なので、`.babelrc`でもコメントや一重引用符などの、JSON5の拡張構文を利用可能です（エディタなどが未対応で波線が出たりするかもしれませんが）。もちろん、ふつうのJSONで書いても全く無問題です。
macOSをMojaveにしたら、Kitematicが動かない

## 問題
macにMojoveが来たのでアップグレードして、特に問題ないなーと思ってたら、Kitematicが動かなくて死んだ。
dockerコマンド打てばちゃんと動くけど、やっぱりGUIツールがほしい。　


> Kitematicが「VirtualBox is not installed. Please install it via the Docker Toolbox.」
  というメッセージが表示され、立ち上がらない。

## 対処
調べたら、Mojoveアップグレード時に変なファイルが出来てたのが原因らしい。
（何のファイルかはよくわかってない）

```
$ cd ~/Library/Application Support/Kitematic/Local Storage
$ ls
    file__0.localstorage
    file__0.localstorage-journal
$ rm file__0.localstorage file__0.localstorage-journal
  -> この２つを削除
```
## 結果
Kitematicを再起動したら、ちゃんと起動しました。
Ruby ハッシュ操作のまとめ（備忘録）

ハッシュ操作のまとめ（備忘録）です。
自分用として記事を作成しましたが、どなたかの役に立てれば幸いです。

##①ハッシュを追加
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
パターン１：
fruits["パイナップル"] = 300
パターン２：
fruits.store("パイナップル",300)
p fruits
# pの出力
# => {"りんご"=>100, "みかん"=>80, "もも"=>200, "パイナップル"=>300}
```
##②ハッシュの中身を変更
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
fruits["りんご"] = 3000
p fruits
# pの出力
# => {"りんご"=>3000, "みかん"=>80, "もも"=>200}
```
##③ハッシュの中身を削除
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
fruits.delete("りんご")
p fruits
# pの出力
# => {"みかん"=>80, "もも"=>200}
```
##④ハッシュの要素数を表示
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
p fruits.length
# pの出力
# => 3
```
##⑤ハッシュの値を配列(each文)で取り出す
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
fruits.each_value do |fruit|
  p fruit
end
# pの出力
# => 100 80 200
```
##⑥ハッシュのキーと値を配列(each文)で取り出す
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
fruits.each do |fruit|
  p fruit
end
# pの出力
# => {"りんご"=>100, "みかん"=>80, "もも"=>200}
```
##⑦ハッシュをキーでソートする（ソート後は配列になる）
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
p fruits.sort
# pの出力
# => [["みかん", 80], ["もも", 200], ["りんご", 100]]
```
##⑧ソート配列になった値をハッシュに戻す
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
p fruits.sort.to_h
# pの出力
# => {"みかん"=>80, "もも"=>200, "りんご"=>100}
```
##⑨ハッシュを値でソートする
```hoge.rb
fruits = {"りんご" => 100, "みかん" => 80, "もも" => 200}
p fruits.sort_by{|k,v| v}
# pの出力
# => [["みかん", 80], ["りんご", 100], ["もも", 200]]
```
##⑩ハッシュのキーをシンボルで表示
```hoge.rb
fruits = {:りんご => 100, :みかん => 80, :もも => 200}
p fruits
# pの出力
# => {:りんご=>100, :みかん=>80, :もも=>200}
```
##⑪ハッシュのキーを省略形で表示
```hoge.rb
fruits = {りんご: 100, みかん: 80, もも: 200}
p fruits
# pの出力
# => {:りんご=>100, :みかん=>80, :もも=>200}
```
##最後に
思いつく限り、ハッシュ操作のあれこれを纏めてみました。
誤字・修正等がありましたら、コメント欄で指摘して頂けると嬉しいです。
MySQLへコネクションプール有り無しでの速度差検証

# MySQL コネクションプール有り無しでの速度検証

MySQLの接続コスト低いらしいってことで確認。

DBのコネクションプール張るとDB障害の時の挙動がめんどくさかったり、DBのIPアドレスがホスト名に対してラウンドロビンで複数返ってくるようなタイプの構成（Auroraの読み込みエンドポイントみたいなヤツ [※こちらの記事参照](https://qiita.com/k_hoso/items/0ab0ae7e19e019685c73)）の時に、ちゃんと分散できてるのっていうのが気になったりで、プールの有り無しの差が無視できるレベルだったら使いたくないよねっていう話。

## 環境

* MySQL 5.7
* Python 3.6
* DB接続に-connector-python使用

※ローカルPCのMySQLに同じPCのPythonでシーケンシャルにDB接続&切断実験。（複数同時接続してる状態にはしない）
※コネクションプールはconnector-pythonの機能利用

つかっているプログラムは [こちら](https://qiita.com/k_hoso/private/f61383734b18c32a65fd)

## 条件

ローカルのMySQLに対して、特定条件でアクセスして速度を測定する。
条件は下記。

* 1o秒間何もしない（平常時の負荷確認用）
* 接続切断だけを5000回実行する。
* SQL1つを5000回実行する。（都度接続）
* SQL1つを5000回実行する＠コネクションプール使用。（接続自体は1回）

※SQL1つ実行毎にリクエスト1回分と見立てるとして（都度、プール共に）

## 計測内容

* 実行時間(s)
* 実行時間/5000回(ms) 
* CPU負荷(%)

## 結果

### 10秒間何もしない（平常時の負荷確認用）
実行時間(s): 10.03, 実行時間/5000(ms): - ※, cpu_average:  7.4%
※何もしないで10秒立つのを待ってるだｋで、ここでは無意味な数値なので値無し。

### 接続切断だけを5000回実行する。
実行時間(s): 13.06, 実行時間/5000(ms): 2.6112, cpu_average: 40.1%

### SQL1つを5000回実行する。（都度接続）

実行時間(s): 14.98, 実行時間/5000(ms): 2.9962, cpu_average: 44.7%

### SQL1つを5000回実行する＠コネクションプール使用。（接続自体は1回）

実行時間(s): 5.46, 実行時間/5000(ms): 1.0926, cpu_average: 42.7%

## 総評

5000回の接続&切断（プール時はプール取得&返却）の1回をリクエスト1回分のDB接続コストって考えると、1リクエストでプール有り無しでの差は 2ms しかないことになる。
影響が大きいと見るか小さい見るかは案件次第。構成かえると結果が変わる可能性もあるけど、2ms だったらプール無くてもいいかな、、っていう感じしますね。。

## 備考

Auroraも一緒だと思うけどいつかやりたい。
【ndnSIM】Interest・DataパケットをIPのパケットに詰め込んだり、元に戻したり

# モチベーション
Information Centric Networking(ICN)のシミュレーションで、ルーティング周りの処理を弄ってトラフィック量の計測がしたい。一番研究が盛んなNDNをベースにして、ちゃんとInterest & Dataパケットは使いたいし、ndnSIM または ndn-cxx + NFD で実装したい。
しかし、ndnSIMにしろndn-cxx + NFDにしろアプリケーション層の研究開発向けっぽくて、ルーティング周りを弄ろうとすると内部実装書き換える必要あるっぽいので、技術力のない自分にはキツい。
仮にアプリケーション層でやりたいことを実装して、中間地点に設置したノードにインストールしても、元々のルーティング処理が良い感じに処理してしまうのでアプリケーション層まで届けられずに転送されてしまう。
そこで、Interest & DataパケットをIPパケットに詰め込んでソケットで送ってしまえばNDNのルーティング処理を通さないので，上位層の自前のコードで色々と処理出来て計測結果取れるよね、みたいな話(日本語が壊滅的に下手すぎてダメ)

# どうするのか
ndn::Interestクラス・ndn::Dataクラス双方にwireEncodeというメソッドが存在する。これはNDNパケットをTLVフォーマットで表現したndn::Block型に変換して返してくれるという優れものである。
ここからさらにuint8_t型定数ポインタに変換してくれるwireというメソッドを使えば良い。ここまで変換すれば、Packet型にPayloadとしてぶち込むことが可能になる。

# 実際のコード (Interestパケットの場合)

```
// 適当にInterestパケットを作成する
ndn::Interest interest(ndn::Name("/ndn.com"));
interest.setInterestLifetime(ndn::time::milliseconds(100000));
interest.setMustBeFresh(true);

// Block型に変換する
ndn::Block block = interest.wireEncode();

// Packetにぶち込む
ns3::Packet packet(block.wire(), (uint32_t)block.size());

// Packetからデータを取り出す
uint8_t *buffer = new uint8_t[packet.GetSize()];
packet.CopyData(buffer, packet.GetSize());

// Block型に復元する
ndn::Block block_restored(buffer, packet.GetSize ());

// Interestパケットに復元する
ndn::Interest interest_restored(block_restored);

// 以下の2行は出力が同じになります
std::cout << interest << std::endl;
std::cout << interest_restored << std::endl;
```

ndn::DataクラスでもwireEncodeメソッドがあるので、Dataパケットでも同様に出来ます。

```
// 適当にDataパケットを作成する
std::shared_ptr<ndn::Data> data = std::make_shared<ndn::Data>();
data->setName(ndn::Name("/ndn.com/content01.html"));
data->setFreshnessPeriod(ndn::time::seconds(10));
static const std::string content = "hogehogeclub";
data->setContent(reinterpret_cast<const uint8_t*>(content.c_str()), content.size());
ndn::security::v2::KeyChain m_keyChain;
m_keyChain.sign(*data);

// Block型に変換する
ndn::Block block = data->wireEncode();

// Packetにぶち込む
ns3::Packet packet(block.wire(), (uint32_t)block.size());

// Packetからデータを取り出す
uint8_t *buffer = new uint8_t[packet.GetSize()];
packet.CopyData(buffer, packet.GetSize());

// Block型に復元する
ndn::Block block_restored(buffer, packet.GetSize ());

// Dataパケットに復元する
ndn::Data data_restored(block_restored);

// 以下の2行は出力が同じになります
std::cout << *data << std::endl;
std::cout << data_restored << std::endl;
```

keyChain.sign()をやっておかないとエラーが出るので注意！
この後はNS-3のSocketとか使って良い感じに指定したノードに送ってあげましょう。
マイグレーションファイルにカラムを追加する方法 #自分用

カラムの追加方法をメモ。


migrationファイルを1度downしてからupする。

rails db:migrate:status
で該当するMigration IDを調べます。

rails db:migrate:down VERSION="調べたMigration ID"
で型を追加し、書き直す
rails db:migrate:up VERSION="調べたMigration ID"

マイグレーションファイルの情報を変更する際は上記の順番で行う。

コンソールで
"チェックしたいカラムがあるモデル".column_namesでカラムチェック。
User.column_names
JavaScriptのタイマー処理　setIntervalとsetTimeout

#動作確認環境
- Mac
- Chrome

#JavaScriptのタイマー処理
処理を遅延させたい、3秒ごとに処理を繰り返したい、というとき、JavaScriptでは以下のような関数を使用します。

**setTimeout関数** ・・・ 指定した時間経過後に処理を実行する
**setInterval関数** ・・・ 指定した時間ごとに処理を実行する

また、それぞれタイマーを停止するための関数も用意されています。
**clearTimeout関数** ・・・ setTimeoutで設定したタイマーを取り消す
**clearInterval関数** ・・・ setIntervalで設定したタイマーを取り消す

###setTimeout関数　clearTimeout関数
指定した時間経過後に処理を実行します。

```js
var log = function(){
  console.log("test");
};

setTimeout(log, 3000);
// 3秒後に"test"と表示されます
```

`setTimeout`では第1引数に指定した時間が経過した後に実行される処理、第2引数に経過時間をミリ秒で指定します。
処理に引数を渡したい場合は、第3引数以降に指定します。

```js
const log = function(msg1){
  console.log(msg1);
};

setTimeout(log, 3000, "Hello");
// 3秒後に"test"と表示されます
```
```js
const log = function(msg1, msg2){
  console.log(msg1, msg2);
};

setTimeout(log, 3000, "Hello,", "Chihiro");
// 3秒後に "Hello, Chihiro" と表示されます
```

一度`setTimeout`を用いてタイマーを設定した後に解除したい場合は、`clearTimeout`関数を使用します。

```js
const log = function(){
  console.log("test");
};

const timer = setTimeout(log, 3000);
clearTimeout(timer);
// タイマーが取り消される。3秒たっても "test" と表示されない。
```

`clearTimeout`では第1引数に取り消したいタイマー処理を設定した`setTimeout`の戻り値を指定します。


###setInterval関数　clearInterval関数
指定した時間ごとに処理を実行します。

```js
const log = function(){
  console.log("test");
};

setInterval(log, 3000);
// 3秒ごとに"test"と表示されます
```

`setInterval`でも第1引数に指定した時間が経過した後に実行される処理、第2引数に経過時間をミリ秒で指定します。
処理に引数を渡したい場合も、`setTimeout`と同様、第3引数以降に指定します。

```js
const log = function(msg1){
  console.log(msg1);
};

setInterval(log, 3000, "Hello");
// 3秒ごとに "Hello" と表示されます
```

`setInterval`を用いてタイマーを設定する場合、指定された処理は指定した時間ごとに実行され続けます。解除したい場合は、`clearInterval`関数を使用します。

```js
const log = function(){
  console.log("test");
};

const timer = setInterval(log, 3000);
clearInterval(timer);
// タイマーが取り消される。3秒たっても"test"と表示されない。
```

`clearInterval`でも第1引数に取り消したいタイマー処理を設定した`setInterval`の戻り値を指定します。
【CSS】謎の空白ができたので、対処法をまとめました。

##謎の空白発生
![スクリーンショット 2018-10-29 22.15.38.png](https://qiita-image-store.s3.amazonaws.com/0/298182/4109512c-2114-c6f9-1dee-12c4220b1d17.png)

ご覧の通り、意図せず謎の空白が生まれました。

##リセットCSSという対処法
対処法１つ目はCSSをリセットするという方法。
やり方は簡単

```css:rei.css
*{
    margin: 0;
    padding: o;
}
```
これだけで下のようになります。
![スクリーンショット 2018-10-30 22.54.12.png](https://qiita-image-store.s3.amazonaws.com/0/298182/ca046b93-bad3-a37c-1465-415c24abd1c7.png)
ただこれだと全体の間が全て詰まってしまいました。

##デベロッパーツールで確認するという対処法
今回はこちらの方法で解決しました。
やり方は下の記事をみてください。かなり便利です。

Chrome デベロッパーツールの使い方まとめ
https://qiita.com/d-dai/items/0b580b26bb1d1622eb46

##謎の空白はデフォルトで設定されていたmarginが原因
調べた結果デフォルトで設定されていたmarginが悪さをしていました。
Webサイトに表示されるときデフォルトで設定されているようなのでお気をつけください。

```css:rei.css
p{
    margin-top:0;
    margin-bottom:0;
}

h1{
    margin-top:0;
}
```
これで謎の空白が解消されました！
![スクリーンショット 2018-10-30 22.54.12.png](https://qiita-image-store.s3.amazonaws.com/0/298182/ea1150e5-29ee-ce69-96d1-656624337303.png)
Angular

■新しく作成

↓↓↓↓↓↓↓ あなたの記事の内容
    ng new hellow-world
───────
    ng  hello-world
↑↑↑↑↑↑↑ 編集リクエストの内容


■移動

    cd hello-world


■visual studio起動

    code .

■サーバー起動(localhost:4200)

    ng serve


■バッククォート(`)で囲う
※シングルクォートで囲うと改行するとエラーになる。

    template: ` `


■コマンドメモ

    Component   ng g component my-new-component 
    Directive  ng g directive my-new-directive 
    Pipe  ng g pipe my-new-pipe
    Service  ng g service my-new-service
    Class  ng g class my-new-class
    Interface  ng g interface my-new-interface
    Enum  ng g enum my-new-enum
Microsoft Teamsのために作成されたO365グループを取得する

#はじめに
MicrosoftがリリースしたTeamsはユーザー管理の基盤としてOffice365(O365)のグループを作成します。
つまり1チームにつき1つのO365グループが作成されます。O365のグループはTeams以外でも使用されますし、しかもチームはデフォルト設定でテナントユーザーであれば誰でも作りたい放題なので、情報システム部門はテナント内のO365グループを把握するのは一苦労です。
というわけでテナント内のO365グループからTeamsのために作成されたO365のグループを取得してみます。

#取得の仕方
取得には[Microsoft Graph API](https://developer.microsoft.com/en-us/graph/docs/concepts/overview)を使用します。
[Graph Explorer](https://developer.microsoft.com/ja-jp/graph/graph-explorer)にアクセスして以下のAPIエンドポイントのURLをGETメソッドで呼び出します。

```
https://graph.microsoft.com/v1.0/groups
```

すると以下のようなJSONファイルが取得されます。
（**Graph Explorerではログインをしないとダミーデータが表示されます**実際のご自身のテナントの情報を取得したい場合は画面左からテナントのアカウントで認証を行ってください。）

```Groups.json
{
    "@odata.context": "https://graph.microsoft.com/beta/$metadata#groups",
    "value": [
        {
            "id": "02bd9fd6-8f93-4758-87c3-1fb73740a315",
            "description": "Welcome to the HR Taskforce team.",
            "displayName": "HR Taskforce",
            "groupTypes": [
                "Unified"
            ],
            "mailEnabled": true,
            "mailNickname": "HRTaskforce",
            "resourceBehaviorOptions": [],
            "resourceProvisioningOptions": [
                "Team"
            ],
            "securityEnabled": false,
            "visibility": "Private",
        },
        {
            "id": "8090c93e-ba7c-433e-9f39-08c7ba07c0b3",
            "description": "Welcome to the team that we've assembled to launch our product.",
            "displayName": "X1050 Launch Team",
            "groupTypes": [
                "Unified"
            ],
            "mailEnabled": true,
            "mailNickname": "X1050LaunchTeam",
            "resourceBehaviorOptions": [],
            "resourceProvisioningOptions": [],
            "securityEnabled": false,
            "visibility": "Private",
        }
        ...
    ]
}
```

このJSONはグループ情報の配列になっています。
そして各グループの```resourceProvisioningOptions```というプロパティに```"Team"```という値が入っていればそのグループはTeamsのために作成されたグループであるということを表しています。

#ODataクエリ
Microsoft Graph APIはODataに対応しており、以下のURLでアクセスすると```resourceProvisioningOptions```に```"Team"```が含まれるグループ、つまりTeamsのために作成されたグループ情報のみが取得できます。

```
https://graph.microsoft.com/beta/groups/groups?$filter=resourceProvisioningOptions/Any(x:x eq 'Team')
```


**注.このODataクエリはv1.0エンドポイントでは対応していないため、bataを使用する必要があります。**

#参考
https://developer.microsoft.com/en-us/graph/docs/api-reference/beta/api/team_list_all_teams
要素の基準点を中心にして中央配置

```css
transform: translate(-50%, -50%);
```

を使うと楽。

```css
html,
body {
  height: 100%;
}
.area {
    position: relative;
    width:100%;
    height:100%;
    background-color: #006d6f;
}
.area .circle {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    width: 64px;
    height: 64px;
    border-radius: 50%;
    background: #fff;
}
.area .triangle {
    position: absolute;
    top: 50%;
    left: 55%;
    transform: translate(-50%, -50%);
    width: 24px;
    height: 24px;
    background:
      linear-gradient(to bottom left, transparent 50%, #006d6f 53%) no-repeat top/100% 50%,
      linear-gradient(to top left, transparent 50%, #006d6f 53%) no-repeat bottom/100% 50%;
}
```

<p data-height="368" data-theme-id="0" data-slug-hash="JmqvWp" data-default-tab="html,result" data-user="horikeso" data-pen-title="JmqvWp" class="codepen">See the Pen <a href="https://codepen.io/horikeso/pen/JmqvWp/">JmqvWp</a> by horikeso (<a href="https://codepen.io/horikeso">@horikeso</a>) on <a href="https://codepen.io">CodePen</a>.</p>
<script async src="https://static.codepen.io/assets/embed/ei.js"></script>
Windowsでphp_curl.dllが使用できない

Windowsにphpをインストール後、ビルトインウェブサーバを起動すると
「PHP Warning:  PHP Startup: Unable to load dynamic library'C:\php\ext\php_curl.dll'」
とコンソールに出力される。

## 動作環境
- Windows10
- PHP 7.1.23

## php.iniを編集する
下記2つの設定を有効にする。
それぞれ行頭のコメントアウト（;）をはずす。

- extension_dir = "ext"
- extension=php_curl.dll

以上で作業は終了。
php_curl.dllが機能するか再度確認する。
Item 24: Favor static member classes over nonstatic

# 24.staticでないメンバクラスより、staticメンバクラスを選択すべし
ネストしたクラスはエンクロージングクラスを補助する目的のために存在すべきである。
もしネストしたクラスをそれ以外の文脈で使用したいなら、トップレベルクラスとして定義するべき。

## ネストしたクラスの種類
ネストしたクラスには4種類あって、

* staticメンバクラス
* 非staticなメンバクラス
* 匿名クラス
* ローカルクラス

がある。staticメンバクラス以外は、内部クラスと呼ばれるものである。
 
本章ではどの場面でどのような理由からどのネストしたクラスを使用すべきか述べる。

### staticメンバクラス
staticメンバクラスはエンクロージングクラスのstaticなメンバの一つで、そのほかのstaticなメンバと同じアクセシビリティのルールに従う。
 
よくあるstaticメンバクラスの使い方の1つは、アウタークラスと伏せて使用した場合にのみ有効なpublic なヘルパークラスとしてである。
例として、計算機のオペレーションを表すenumを考える（Item34）。
オペレーションenumはCalculatorクラスのpublic staticなメンバークラスであるべき。
Calcuratorの利用者は、オペレーションを Calculator.Operation.PLUSや Calculator.Operation.PLUS のように参照できる。

### 非staticメンバクラス
非staticなメンバクラスのインスタンスは、暗黙的にエンクロージングインスタンスへの参照を持つ。
非staticなメンバクラスの中のインスタンスメソッドにおいて、エンクロージングインスタンスのメソッドを呼ぶことができ、qualified thisを使用してエンクロージングインスタンスへの参照を得ることができる。
（qualified thisはエンクロージングクラス.thisのことを指している）
エンクロージングインスタンス抜きで非staticなメンバクラスのインスタンスを生成することは不可能、つまり、独立にさせたいのならstaticメンバクラスを選択する必要がある。
 
非staticメンバクラスのインスタンスと、エンクロージングインスタンスの参照が形成されるのは、メンバクラスのインスタンスが生成されたときであり、そのあとに変更されることはない。
通常、エンクロージングクラスのインスタンスメソッドから、非staticなメンバクラスのコンストラクタが呼ばれることによって、参照が形成される。

非staticメンバクラスのよくある使い方は、Adapterである。
Adapterを用いると、エンクロージングクラスのインスタンスが別のクラスのインスタンスであるかのように見せることができる。
具体的には、MapのkeySetやvaluesメソッドで返されるcollection的な見た目のものは、非staticメンバクラスを使用している。
ListのIteratorなんかもそう。

```java
    public Iterator<E> iterator() {
        return new Itr();
    }

    /**
     * An optimized version of AbstractList.Itr
     */
    private class Itr implements Iterator<E> {
    ...
    }
```


もし、メンバクラスがエンクロージングインスタンスにアクセスする必要がないのであれば、常にstaticとして宣言しておくべきである。
なぜなら、この間の参照を生成するのに時間とメモリが食われるということと、この参照がなければガベージコレクションの対象となっているかもしれないからである（Item7)

private static なメンバークラスは、エンクロージングクラスのコンポーネントの一部として表される。
例えば、Mapインスタンスを考えてみると、多くのMapの実装では、Mapのなかのkey-valueのペアとしてEntryオブジェクトを保有する。
Entryのメソッド（getKey、getValue、setValue）はmapのメソッドにアクセスする必要がないので、entryを非staticなクラスにするのは無駄である。
非staticにしても動くが、mapへの余計な参照が増えるだけでメモリの無駄使いである。

ネストクラスについて、外部公開するか迷っている場合も、staticにするか非staticにするかの選択は重要である。
ネストクラスを外部公開した場合、非staticからstaticに変えることはできない。（後方互換性を犯すことになる）

### 匿名クラス
匿名クラスは他のクラスに属するというよりは、使用される時に宣言、インスタンス化が同時に行われるといえる。
匿名クラスは非staticな文脈であれば、エンクロージングクラスのインスタンスを保有することができる。
しかし、staticな文脈で匿名クラスが書かれていたとしても、constant variable(finalが付与されたprimitiveかStringの変数)でない限りはstaticメンバをもつことはできない。

#### 匿名クラスの制限
* 匿名クラスには以下のような制限がある。
* 宣言された箇所以外でインスタンス化することはできない
* instanceofでテストできないなど、クラスの名前が必要となる処理はできない
* 複数インターフェースを実装したり、クラスを継承してインターフェースを実装したりすることができない
* 匿名クラスの利用者は、匿名クラスのスーパークラスのから継承したものしか呼び出せない

lambdaが導入されるまでは、小さな関数オブジェクトやプロセスオブジェクト（？）を生成する手段として匿名クラスが用いられてきたが、現在はlambdaのほうが好まれる。
その他、匿名クラスのおもな使用例としては、staticなファクトリメソッドの実装で用いられる。（Item20）

### ローカル内部クラス
ローカル内部クラスは、ローカル変数と同様のかたちで宣言され、スコープも同じかんじ。
可読性のために短く保つべき。

## まとめ
ネストクラスは4つあり、それぞれ使い道が違う。
メソッドの外側でvisibleである必要があったり、メソッドの内部に置くには長すぎる時にはメンバクラスを用意する。
メンバクラスのそれぞれのインスタンスがエンクロージングクラスのインスタンスにアクセスする必要があるのならば、非staticにすべき。それ以外はstaticにすべき。

メソッド内のクラスに関して、1か所のみで使い、動きを規定してくれるような既存のクラスがある場合は匿名クラスを使う。それ以外はローカル内部クラスを使う。