OmniAICreator/Qiita-1.07M huggingface dataset:
[UiPath][.NET]And/OrとAndAlso/OrElseの違い

## 前段
UiPathで"If"アクティビティを利用しているとき、複数のIfを重ねると見栄え的につらいので、なんとか出来ねーかなと調べていたところ、「AndAlso/OrElse」なるものがあることを知った。
実際に使ってみたところ、自分のケースでは効果があった。また開発の一環で非エンジニアに説明をする機会があり、その違いを簡単にまとめたのでQiitaでも書いてみようと思った。
*（Flowchart使えよ、というツッコミはなしで………）*

# TL;DR
__上手に使えば__AndAlso/OrElseは効果的かな、と思った

## それぞれの比較
### And/Or
- 結合した要素(変数、数式)を「全部」評価する
- 要素を左側からひとつずつ評価していく過程で、全体の評価結果が確定した場合でも、**問答無用で「すべて評価」する**
- 全部評価するので、要素の結合順序は問わない。要素同士の可換性がある
    - 例えば下記コードは、最終的にすべて同様の評価プロセスを経る
        - `A And B And C`
        - `B And C And A`
        - `C And B And A`
    - 要素ごとの評価結果によらず、全部の要素が評価されるため

### AndAlso/OrElse
- 結合した要素を「全部または一部」評価する
- 要素を左側からひとつずつ評価していく過程で、ある要素を評価した段階で全体の評価が確定した場合、**「以降の要素を評価しない」**
- 場合によって全部の要素を評価しないため、要素の結合順序の影響を受ける。要素同士の可換性はない
    - 例えば前述のコードと類似する下記コードは、いずれも評価プロセスが異なる
        - `A AndAlso B AndAlso C`
        - `B AndAlso C AndAlso A`
        - `C AndAlso B AndAlso A`
    - 要素ごとの評価結果およびその位置によって、評価されない要素が異なる

## ケース紹介
自分が使ったのは、下記のようなコードをズボラしたとき。
datarows[]には任意のDataTableに対してselectでDataRowを抽出した結果を入れるけど、その結果がゼロである可能性がある。

```
if(datarows.count > 0){
    if(datarows(0).item("total") < 0){
        console.write(datarows(0)("label").toString);
    }
}
```

上記のようにネストされたIfを外したいときに、下記のように書くとエラーが起こる。

```
if(datarows.count > 0 And datarows(0).item("total") < 0){
    console.write(datarows(0)("label").toString);
}
```

なぜなら、結果がゼロであった場合に次のプロセスを踏むから。

1. `datarows.count > 0` が `false` を返す
2. `And`で結合しているので、上記の結果は次の要素の評価に影響しない
3. そのためプログラムは**そのまま**`datarows(0).item("total") < 0`**を評価する**
4. しかし`datarows(0)`は`null`であり、上記の文はエラーとなる
5. したがってifの条件判定においてエラーが発生する

これが、`AndAlso`に置き換えるとどうなるか。

```
if(datarows.count > 0 AndAlso datarows(0).item("total") < 0){
    console.write(datarows(0)("label").toString);
}
```

1. `datarows.count > 0` が `false` を返す
    - （`datarows.count = 0`）、`datarows(0)`は`null`になる
2. `AndAlso`で結合しているので、上記の結果を元に、結合された文全体を評価する
3. すでに上記の結果で`false`が出ているため、文全体では`false`となることが確定している
4. 文全体での結果が確定しているため、残りの要素は評価しない
5. したがって`datarows(0).item("total") < 0`は評価されないため、**エラーとならない**

---

- 2018/11/26
    - コメントでのご指摘をもとに修正。
【SAPUI5】Bootstrapとは？

##Bootstrapとは
Bootstrapは一般的には以下のように定義されています。
>電源投入後あるいはリセットの後に、コンピューター上のメモリーに基本的なソフトウェアを読み込むことを指す。
出典: フリー百科事典『ウィキペディア（Wikipedia）』

SAPUI5では、ページが開かれたとき、最初にSAPUI5のライブラリやテーマなどを読み込むスクリプトのことを指します。
SAPUI5のアプリケーションとして動かすために必須なのですね。
（Bootstrapという名前のフレームワークがありますがそれとは別物です）
##どこに書くのか
はじめに、[前回の記事](https://qiita.com/tami/items/05014dd40577cc92ccca)でご紹介した手順でHelloworldのページを作っておきます。
index.htmlのファイルは以下のようになっています。

```html
<!DOCTYPE html>
<html>
	<head>
		<meta http-equiv="X-UA-Compatible" content="IE=edge"/>
		<meta charset="UTF-8">
		<title>Hello World App</title>
	</head>
	<body>
		<p>Hello World</p>
	</body>
</html>
```

headタグの後に以下のようにコードを追加します。
ひとつ目のscriptタグの中がBootstrapです。

```html
<!DOCTYPE html>
<html>
	<head>
		<meta http-equiv="X-UA-Compatible" content="IE=edge"/>
		<meta charset="UTF-8">
		<title>Hello World App</title>
		<!--以下を追加-->
	    <script
	       id="sap-ui-bootstrap"
	       src="https://sapui5.hana.ondemand.com/resources/sap-ui-core.js" 
	       data-sap-ui-theme="sap_belize"
	       data-sap-ui-libs="sap.m"
	       data-sap-ui-compatVersion="edge"
	       data-sap-ui-preload="async" >
	    </script>
	    <script>
	       sap.ui.getCore().attachInit(function () {
	           alert("UI5 is ready");
	       });
	    </script>
	    <!--以上を追加-->
	</head>
	<body>
		<p>Hello World</p>
	</body>
</html>
```

##Bootstrapの中身
|項目  |指定するもの  |
|---|---|
|id  |固定値 "sap-ui-bootstrap"  |
|src |SAPUI5 coreライブラリが格納されている場所  |
|data-sap-ui-theme |UIのテーマ  |
|data-sap-ui-libs |ページで使用するUIのライブラリ  |
|data-sap-ui-compatVersion |"edge"を指定すると、SAPUI5の最新機能が使える（任意指定） |
|data-sap-ui-preload |ライブラリを同期で読み込むか(sync)、非同期で読み込むか(async)を指定する。パフォーマンス向上のためasyncを指定することが推奨されている|

##attachInitメソッドについて
data-sap-ui-preloadを"async"（非同期）とした場合、必要なライブラリがすべて読み込まれたタイミングをアプリケーションが知る必要があります。このためにattachInitメソッドを使用します。
今回は、attachInitメソッドの中でアラートを出力するようにしています。
##実行結果
実行結果は以下のようになります。
<img width="703" alt="hcp_16.png" src="https://qiita-image-store.s3.amazonaws.com/0/276021/2ecd261d-06fb-7a57-f8cd-0dad6d73b2ac.png">
##参考にしたページ
[Bootstrapping: Loading and Initializing](https://sapui5.hana.ondemand.com/#/topic/a04b0d10fb494d1cb722b9e341b584ba)
[Get Started: Setup and Tutorials-Walkthrough-Step 2: Bootstrap](https://sapui5.hana.ondemand.com/#/topic/fe12df2e338e43598977d09f3d191b7b)
git stash を実行したブランチで pop するコマンド、 git bpop を作った

# 動機

Git で、編集途中のファイルを `git stash` して、別のブランチに移動することがあります。作業が終わって元のブランチに戻ってきた時に、`stash pop` するのを忘れたり見失ったりしそうで不安でした。

今のブランチで実行した `stash` の一覧を表示して `pop` する方法があるのでは、と思ったのですが、それらしいのが見つからなかったので作りました。

特に最近は、毎朝、TODO リストにある全タスクに 10 分ずつ着手する、という作業のスタイルを試していて、たくさんの `stash` を管理するのに役に立っています。

# スクリプト

以下を `git-bpop` というファイル名でパスの通った場所に保存します。

```bash
#! /bin/bash

set -e

BRANCH=$(git rev-parse --abbrev-ref HEAD)
STASH=$(git stash list | grep -F ": WIP on $BRANCH:" | tail -r)

IFS=$'\n'
for S in $STASH; do

    REV=$(echo "$S" | sed -e 's/^\(stash@{[0-9]*}\):.*/\1/')

    echo '------------------------------------'
    echo $S
    echo '------------------------------------'
    if [ "$1" = 'pop' -o "$1" = 'p' ]; then
        git --no-pager diff "HEAD...$REV"
        echo
        git stash pop "$REV"
        exit
    else
        git diff "HEAD...$REV"
    fi
done
```

やっていることは、`git stash list` で表示される `WIP on ブランチ名` を、今のブランチ名で `grep` して、`diff`、`stash pop` しているだけです。複数の stash が見つかったら一番古いものを `pop` します。

# 使い方

作業中のブランチから離れるときに、普通に `git stash` します。

```bash
## 現在のブランチは branch-1
$ git branch
* branch-1
  master

## 何か変更します。
$ echo bbb >> test.txt

## 別の作業が発生したので、変更を stash して、
$ git stash
Saved working directory and index state WIP on branch-1: 90dd8a9 init
HEAD is now at 90dd8a9 init

## master に移動します。
$ git checkout master
Switched to branch 'master'

## master ブランチには stash が無いことを確認。
$ git bpop
$
```

別の作業が終わって、最初のブランチに戻ってきたら、`$ git bpop` で `stash` の `diff` を確認します。

```diff
$ git checkout branch-1
Switched to branch 'branch-1'

$ git bpop
------------------------------------
stash@{0}: WIP on branch-1: 90dd8a9 init
------------------------------------
diff --git a/test.txt b/test.txt
index 72943a1..dbee026 100644
--- a/test.txt
+++ b/test.txt
@@ -1 +1,2 @@
 aaa
+bbb

```

`diff` を適用して問題なさそうだったら、`$ git bpop pop` で `stash pop` します。

```diff
$ git bpop pop
------------------------------------
stash@{0}: WIP on branch-1: 90dd8a9 init
------------------------------------
diff --git a/test.txt b/test.txt
index 72943a1..dbee026 100644
--- a/test.txt
+++ b/test.txt
@@ -1 +1,2 @@
 aaa
+bbb

On branch branch-1
Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git checkout -- <file>..." to discard changes in working directory)

        modified:   test.txt

no changes added to commit (use "git add" and/or "git commit -a")
Dropped stash@{0} (076c635f56852e3c367f0fd435d906852894a7c3)
```

# 他のアイディア

当初は `git checkout` 時に自動で `stash pop` することを考えていました。全ての `stash` が全部自動で適用されてしまうのはナシかなと思って止めましたが、、。

「次回必ず pop する」マーク付きで `stash` するコマンドを作って、`pop` はフックで実行する、みたいなのも便利かもしれません。
PostgresqlのRDSからCSVエクスポートする方法

色々試して、結局 `\COPY (SELECT * FROM XXX)` の形じゃないと取れなかった。


psql -U aaa -h bbb.ccc.ap-northeast-1.rds.amazonaws.com -p 5432 -d eee -c "\COPY (SELECT * From public.fff_tables) TO '/tmp/fff_tables.csv' WITH CSV DELIMITER ','"


`COPY`はsuperuserじゃないと使えないと言われ(`must be superuser to COPY to or from a file`とか言われる)、
`\COPY table_name`だとなぜか0件で出力された。
【洗面所IoT　No.0】PJ開始にあたり

はじめまして。

簡単に自己紹介と今回の目的を記載していきます。

【自己紹介】
すでに５０歳を超えるITオタク。
それなりの会社のそれなりの役職につき、それなりの仕事をしています。
昔は、ORACLEやInfomixを始めとしたRDBMSの性能評価やポーティング支援を、RDBMSを有効活用するためのネットワークが必要となりOSPFやらBGP4やらのコンフィグレーションを書いておりましたが、だんだん現場から離れていき、M&Aやら出資案件をしていたら上海に飛ばされてしまいました。

![IMGP2262.JPG](https://qiita-image-store.s3.amazonaws.com/0/318786/da1b2c82-79e9-5e99-206f-fd45836b9e89.jpeg)

日本に戻ってきて医療関係ITに従事しておりましたが、縁があり現在は全く違う仕事をしております。

【PJ目的】

M2M、ユビキタス、IoTを考えるに当たり意識していることは、「大量のデータを保存し、分析した結果を表示する（次のアクションにつなげる）」ことであり、特に今回は短時間の表示にて必要十分な情報をタイミングよく提供する方法を模索することを目的としています。
そのため、これからいろいろと試行錯誤をしていきますが、問題なのはここ最近記憶力が衰えている事。そこでBlog形式にて作業内容を記載していくことにしました。

　日々の生活の中で、携帯電話以外の電子デバイスといえはTVを始めとした生活家電。
　以前から、生活家電メーカー各社と話す機会は多々ありましたが、結局機能に特化しておりIoT化に後ろ向き（今はわかりませんが・・・）ならば自分で作る事にしました。

今回目をつけたのは・・・「洗面台」

朝の忙しい時に、短時間でも必ず家族全員が立ち寄る「洗面台」「トイレ」「玄関」をIoTの情報出力端末にして必要十分な情報を提供することが可能なのか？

色々と試していきたいと思います。
RetrofitのGETにハッシュ(hash)をクエリに入れて投げたい

サーバーの都合上変な投げ方をする必要があったのでメモ

```
build.gradle
dependencies {
　　....
    def retrofitVersion = '2.4.0'
    implementation "com.squareup.retrofit2:retrofit:$retrofitVersion"
    implementation "com.squareup.retrofit2:adapter-rxjava:$retrofitVersion"
    implementation "com.squareup.retrofit2:converter-gson:$retrofitVersion"
    implementation 'com.squareup.okhttp3:logging-interceptor:3.8.1'
}
```

## GETのクエリパラメータにhashを入れたい

https://github.com/square/retrofit/issues/645#issuecomment-60836039 に書いてた

```
interface TestService {

    @GET("/hoge/index")
    fun index(@Query("user_id") userId: String,
              @Query("params") params: String,
              @QueryMap fields: Map<String, String>
    ): Call<String>
}
```

Bodyだと別のやり方があってよく見かけるし、配列を入れる場合もできたがhashが結構探した

[android - How to post data using HashMap in retrofit? - Stack Overflow](https://stackoverflow.com/questions/42437688/how-to-post-data-using-hashmap-in-retrofit) がbody
[【Android】RetrofitのGETリクエストで配列を渡したい - Qiita](https://qiita.com/circularuins/items/ed35a39bb25cc0c2fb16)
GPSデータの入ったCSVファイルからマップデータ(HTML)を作成する

本記事では、緯度・経度などのGPSデータを地図上に反映させた、マップデータを作成するスクリプトを紹介します。

## GPSデータの入ったCSVファイル
前回書いた記事で、GPSデータが入ったCSVファイルを作りました。
前回：https://qiita.com/vegaukulele/items/e03cf83479a504344ca9
内容はこんな感じです。

```
gps log.csv
time,latitude,longitude,altitude,timestamp,horizontal_accuracy,vertical_accuracy,speed,course
2018/11/18 15:52,34.5,136.53,9.39266777,1542523726,65,10,-1,-1
2018/11/18 15:52,34.6,136.3,9.39266777,1542523717,65,10,-1,-1
2018/11/18 15:52,34.7,136,7.835945129,1542523942,10,4,0,-1
```

少し読みにくいですが、時間,緯度,経度,高度,... とデータが並んでいます。
数値は適当です。

## CSVファイルを読み込んでデータを整理
それではスクリプトの説明に入っていきます。
まずはインポートするライブラリから。

```python:gps_mapmaker.py

# 地図を作成するWebアプリ「Leaflet」を利用したライブラリ
import folium 
```
今回は「folium」というライブラリを使用します。あらかじめpipでインストールをお願いします。

続いてCSVファイルを開きます。

```py

# あらかじめ空のリストを2つ用意する
gps_list = []
gps_data = []
# 保存されているgps_log.csvを読み込みモードで開く
with open('gps_log.csv', mode = 'r', encoding = 'utf-8') as f:
# next()で2番目から(csvでは2行目から)データを扱う
    next(f)
# csvのrowそれぞれに対して、改行を省いてカンマで区切ってリストにする
# さらにリストのうち先頭3つ(取得時間、緯度、経度)を抽出する
    for line in f:
        gps_list = line.rstrip('¥n').split(',')
        gps_data.append(gps_list[:3])
```
これでgps_dataリストに必要なデータを格納できました。しかしこのリストは文字列型のリストなので、foliumで扱えるように手を加えます。

## 読み込んだ文字列型リストを小数型リストに変換
```python
gps_data_flt = []
time_data = []
for d in gps_data: # gps_dataリストの各要素(リスト型)に対して処理を実行
    time_data.append(d[0]) # 取得時間のリストを別途用意する
    d.pop(0) # 取得時間の要素を削除する
    for i in d: # 要素(リスト型)の中の要素[文字列型]を順に[小数型]に変換
        gps_data_flt.append([float(i) for i in d])
```
gps_dataリスト内の要素を「取得時間」リストと「緯度,経度」リストに分け、「緯度,経度」リストの要素をfloat型にしました。まどろっこしいコードな気がしますが、試行錯誤した結果なのでご容赦ください。

## foliumのメソッドを使ってマップデータを作成
編集したデータを使ってマップデータを作ります。

```py
# 地図の基準地点として、最後のログの位置を設定
last_log = gps_data_flt[-1]
# 基準地点と初期の倍率を指定し、地図を作成する
map = folium.Map(location=last_log, zoom_start=30)
# 記録した各ログをマークし、popupを自身の計測時間とする
for f,t in zip(gps_data_flt,time_data):
    marker = folium.Marker(f, popup=t)
    map.add_child(marker)

# 置いたマーカー同士を線で結ぶ
gps_line = folium.PolyLine(locations=gps_data_flt)
map.add_child(gps_line)

# 地図をhtml形式でこのスクリプトと同じディレクトリに出力
map.save(outfile= "gps_map.html")
```

作成したhtmlファイルをブラウザで見てみましょう。
![キャプチャ.PNG](https://qiita-image-store.s3.amazonaws.com/0/315296/ea469406-e516-4c24-5019-0656b24065be.png)
マップ上にマーカーがプロットされてますね。
マーカーをクリックするとポップアップ(取得時間)を見ることができます。

説明は以上になります。かなり苦戦しましたが、なんとか作れました。
リストや辞書などの基礎的な処理はなんだかんだ言って大事ですね。



###参考にしたURL：

「Folium 0.5.0 documentation」
http://python-visualization.github.io/folium/docs-v0.5.0/modules.html

「Pythonのfoliumパッケージで地図を描いてみる」
https://qiita.com/kzkt0713/items/de85668dca14462c182d

「Python + folium で Strava の "全"記録を地図で可視化 🚲」
https://hiboma.hatenadiary.jp/entry/2017/09/13/094056

##補足：Pythonista3でやる場合
Pythonista3の場合はStashを使ってインストールする必要があります。具体的な方法は以下を参照ください。
「まだPythonista3使ってないの？ー基本操作・StaShインストール編ー」
https://qiita.com/n_oshiumi/items/4a647f2c8a3c209fd87b

Stashでfoliumをインストールしたら、brancaというライブラリも一緒にインストールしてください。folium自身がbranceを使用するようです。

また、foliumの使用にはnumpyも必要になるのですが、Pythonista3にはnumpyがデフォルトでインストールされています。私はそれに気づかずインストールしてしまい、スクリプトがうまく動かず、結構悩みました。一度Pythonista3をダウンロードし直してfoliumとbrancaだけインストールすると動きました。気を付けてください。
アルファベット進数

「アルファベット進数」という訳の分からない造語を作ってしまった( '-' )

##プログラム

```py
"""
処理内容（例：「731」が渡された時）：
- １． 731 % 26 = 3 ←「C」で確定
- ２． 731 / 26 = 28 ←「26」より大きいので次の処理に使う
- ３． 28 % 26 = 2 ←「B」で確定
- ４． 28 / 26 = 1 ←「26」より小さいので「A」で確定
- ５． 確定したモノを逆順で出力する ←「ABC」
"""

import sys
import math

ALPHABET = ["A","B","C","D","E","F","G","H","I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W","X","Y","Z"]
result = []

def alphabet_decimal(v):
    quotient = math.floor(v / len(ALPHABET))
    surplus = v % len(ALPHABET)
    quotient -= 1 if surplus == 0 else 0
    surplus = len(ALPHABET) if surplus == 0 else surplus
    result.append(surplus)
    if len(ALPHABET) < quotient:
        alphabet_decimal(quotient)
    elif len(ALPHABET) < v:
        result.append(quotient)
    return "".join([ALPHABET[i - 1] for i in reversed(result)])

print(alphabet_decimal(int(sys.argv[1])))

```

##実行結果

```sh
$ python editXlsx.py 1
A

$ python editXlsx.py 26
Z

$ python editXlsx.py 27
AA

$ python editXlsx.py 731
ABC

$ python editXlsx.py 3909967
HNKYI
```

####余談


Pythonのモジュール「`openpyxl`」を使っていて、**「最大行・最大列の範囲を指定する」**をしようとした際、方法論が見当たらなかった事がそもそものきっかけ。

```py
# モジュールをインポートして、
# Excelファイルを取得し、
# Sheet1を指定して、
# A1:X3の範囲を取得する。
import openpyxl
book = openpyxl.load_workbook("hoge.xlsx")
sheet = book.get_sheet_by_name('Sheet1')
ranges = sheet["A1:X3"]
```

上記のコードでは「A1:X3」とハードコーディングで指定しているが、実際のプログラムでこんな事をする訳がない。

`sheet.max_column`と`sheet.max_row`を使えば何とかできそうな気もしたけど、列名を取得する方法が見当たらない。。。

「だったら作ってしまえ！」っていう( '-' )←

<br>

「26進数になってるな...どうやったら進数ってプログラム組めるだろう」ってところから組んでみて、法則見つけるまで少し時間かかったけど、何とか自力でやったった( '-' )!!!

もっと良い方法あったら教えて下さい。
プログラマー向けの（？）数理論理学

「プログラマー向けの（？）数理論理学」のまとめページです。更新履歴や関連情報なども掲載します。

### 進捗状況

あまり良くありません。今後更新頻度が落ちるかもしれません。

### 連載一覧

* [プログラマー向けの（？）数理論理学（１）数学的言明](https://qiita.com/pizyumi/items/c562ac384d759564287a)
* [プログラマー向けの（？）数理論理学（２）証明と推論規則と仮定](https://qiita.com/pizyumi/items/4e1c0c7a9898d4f8c06d)
* [プログラマー向けの（？）数理論理学（３）ウェブアプリ化](https://qiita.com/pizyumi/items/02a13e95dfb6038fb0b9)
* [プログラマー向けの（？）数理論理学（４）証明図](https://qiita.com/pizyumi/items/b8d4292d8ebe0b24fb0f)
* [プログラマー向けの（？）数理論理学（５）含意のみに関する主要な定理](https://qiita.com/pizyumi/items/a55ba131e809458f1138)
* [プログラマー向けの（？）数理論理学（６）否定に関する推論規則](https://qiita.com/pizyumi/items/c1a859ebef6009fbbe5f)
* [プログラマー向けの（？）数理論理学（７）連言に関する推論規則](https://qiita.com/pizyumi/items/b69939c6fbda7edc367f)
* [プログラマー向けの（？）数理論理学（８）選言に関する推論規則](https://qiita.com/pizyumi/items/2b0802c910136a490923)
* プログラマー向けの（？）数理論理学（９）同値に関する推論規則（予定）
* プログラマー向けの（？）数理論理学（１０）推論規則コマンドの追加等（予定）
* プログラマー向けの（？）数理論理学（１１）否定と含意に関する主要な定理（予定）
* プログラマー向けの（？）数理論理学（１２）連言に関する主要な定理（予定）
* プログラマー向けの（？）数理論理学（１３）選言に関する主要な定理（予定）
* プログラマー向けの（？）数理論理学（１４）同値に関する主要な定理（予定）
* プログラマー向けの（？）数理論理学（１５）命題論理のその他の主要な定理（予定）
* プログラマー向けの（？）数理論理学（１６）カテゴリー機能（予定）
* プログラマー向けの（？）数理論理学（１７）証明図の画像保存（予定）
* プログラマー向けの（？）数理論理学（１８）論理式のパーサ（予定）
* プログラマー向けの（？）数理論理学（１９）正規化（予定）
* プログラマー向けの（？）数理論理学（２０）述語論理（予定）
* プログラマー向けの（？）数理論理学（２１）述語論理の推論規則（予定）
* プログラマー向けの（？）数理論理学（２２）代入に関する推論規則（予定）

### 関連記事

* [形式化数学入門1](https://qiita.com/pizyumi/items/24e5ba843133059fd74a)

* 数学ゲーム（定理証明ゲーム）を作ろう（１）構想を練ってみる（予定）

### 今後取り扱うかもしれないこと

#### 数学

* 述語論理
* 公理的集合論
* .etc

#### 機能追加・改善

* 論理式のパーサ作成
* 証明図上で直接証明を作成する機能
* 数学記述言語の作成
* ログイン機能
* 公開機能
* メタデータ追加
* 1つの数学的命題に対する複数の証明の扱い

### 関連情報

#### GitHub

「rena」という名称で公開しています。

[https://github.com/pizyumi/rena](https://github.com/pizyumi/rena)

#### Twitter

近々Twitterでも形式化数学の情報（様々な定理の形式的証明など）や開発の進捗状況を発信していきたいと思っています。

#### ウェブページ

まだまだ先になりそうですが、形式化数学に関するウェブページを作成したいです。

### 更新履歴

#### 2019/1/26

* （８）選言に関する推論規則・・・投稿

#### 2018/12/3

* （７）連言に関する推論規則・・・投稿

#### 2018/11/30

* （６）否定に関する推論規則・・・投稿

#### 2018/11/26

* （５）含意のみに関する主要な定理・・・投稿

#### 2018/11/23

* （４）証明図・・・証明図のCSSとHTMLを変更
* （４）証明図・・・証明図作成のロジックを大幅に改良・バグ修正
* （４）証明図・・・説明の詳細化

#### 2018/11/22

* （２）証明と推論規則と仮定・・・含意導入規則のロジックを大幅に改良
* （２）証明と推論規則と仮定・・・説明の詳細化

#### 2018/11/12

* （４）証明図・・・投稿

#### 2018/11/9

* （２）証明と推論規則と仮定・・・説明追加
* （３）ウェブアプリ化・・・投稿

#### 2018/11/7

* （２）証明と推論規則と仮定・・・投稿

#### 2018/11/6

* （１）数学的言明・・・投稿
[iOS][Swift] Xcodeでビルド番号の自動更新

Gitのコミット数をビルド番号にセットする方法です。

- 簡単
- Gitのバージョン履歴を汚さない
- CFBundleVersionを自動更新
- バージョン番号を更新してほしいときだけ更新される



##手順
Build phaseからNew Run Script Phaseを選択し、
<img width="917" alt="01.png" src="https://qiita-image-store.s3.amazonaws.com/0/82835/cf984308-e2cb-cf0d-2ecc-95fe139c03f8.png">

以下のコードをRun Scriptに記載します。

```
# Set the build number to the count of Git commits
buildNumber=$(git rev-list HEAD | wc -l | tr -d ' ')
/usr/libexec/PlistBuddy -c "Set :CFBundleVersion $buildNumber" "${PROJECT_DIR}/${INFOPLIST_FILE}"
```
<img width="1176" alt="02.png" src="https://qiita-image-store.s3.amazonaws.com/0/82835/0d3287eb-8368-e8bd-2687-84be68bf5db0.png">

参考：
https://stackoverflow.com/a/24750392
KotlinでByteArrayをLong, Intに変換する

バイトオーダーがBigEndianであることを前提にしています。

# JVM環境の場合

JVM環境では`ByteBuffer`クラスが使えるので、簡単にByteArrayを数値に変換することができます

```jvm.kt
// ByteArray -> Long
val longBytes = byteArrayOf(1, 1, 1, 1, 1, 1, 1, 1)
ByteBuffer.wrap(longBytes).getLong()

// ByteArray -> Int
val intBytes = byteArrayOf(1, 1, 1, 1)
ByteBuffer.wrap(intBytes).getInt()
```

# Kotlin/Native環境の場合

Kotlin/Native環境の場合は`ByteBuffer`クラスが使えないので、以下のような関数を実装します。

```native.kt
// 8バイトの配列をLong型に変換します。
fun byteArrayToLong(byteArray: ByteArray?): Long {
    byteArray ?: return 0
    var result: Long = 0
    for (i in 0..7) {
        val value = byteArray.getOrNull(i) ?: 0
        result = result shl 8
        result = result or value.toUByte().toLong()
    }
    return result
}

// 4バイトの配列をInt型に変換します。
fun byteArrayToInt(byteArray: ByteArray?): Int {
    byteArray ?: return 0
    var result = 0
    for (i in 0..3) {
        result = result shl 8
        result = result or byteArray[i].toUByte().toInt()
    }
    return result
}

```

# テスト

```test.kt
import kotlin.experimental.and
import java.nio.ByteBuffer

// 8バイトの配列をLong型に変換します。
fun byteArrayToLong(byteArray: ByteArray): Long {
    var result: Long = 0
    for (i in 0..7) {
        result = result shl 8
        result = result or (byteArray[i] and 0xFF.toByte()).toLong()
    }
    return result
}

// 4バイトの配列をInt型に変換します。
fun byteArrayToInt(byteArray: ByteArray): Int {
    var result: Int = 0
    for (i in 0..3) {
        result = result shl 8
        result = result or (byteArray[i] and 0xFF.toByte()).toInt()
    }
    return result
}

fun main(args: Array<String>){  
    val longBytes = byteArrayOf(1, 1, 1, 1, 1, 1, 1, 1)
    val intBytes = byteArrayOf(1, 1, 1, 1)

    println("ByteBuffer#getLong(): ${ByteBuffer.wrap(longBytes).getLong()}")
    println("ByteBuffer#getInt(): ${ByteBuffer.wrap(intBytes).getInt()}")
    
    println("byteArrayToLong(): ${byteArrayToLong(longBytes)}")
    println("byteArrayToInt(): ${byteArrayToInt(intBytes)}")
}
```

実行結果

```
[Running] cd "/Users/hoge" && kotlinc-jvm test.kt -include-runtime -d test.jar && java -jar test.jar
Picked up JAVA_TOOL_OPTIONS: -Dfile.encoding=UTF-8
Picked up JAVA_TOOL_OPTIONS: -Dfile.encoding=UTF-8
ByteBuffer#getLong(): 72340172838076673
ByteBuffer#getInt(): 16843009
byteArrayToLong(): 72340172838076673
byteArrayToInt(): 16843009
```

# 参考
- https://stackoverflow.com/questions/44067297/bytearray-to-float-in-kotlin
- https://stackoverflow.com/a/29132118/4791194
業務支援用のスクリプト言語を決める

#はじめに
プログラマに限らず 多くの仕事では業務で使う言語以外の作業が発生する
たとえば　ファイル名を規則的にRenameしたり
ファイルの中のCSVデータを規則的に変換したり
ログファイルから必要なものだけを抽出したり

そういう作業を私はあまり任されなかったのだけど
現場によっては 私が作る必要も出てくる
そんなときに私はメインのスクリプト言語をきめていなかった

C＋＋で作ったりもしていたが
ちゃんと スクリプト言語決めたいとおもって　各状況をまとめてみた

#必要要素
業務支援なので　お手軽なものがいい
自分だけが使うとも限らず　他人もすぐ使える物がいい
基本的には実行速度はあまり要求されない
コンパイルなしで使えるとありがたがられる
最近はWindowsとMacの両方に対応することがマスト
OSに最初からインストールされている言語だとありがたがられる


#コンパイル言語
##Java
開発にはSDKが必要
利用するためにはJVMのインストールが必要だが、入ってることが多い
GUIはライブラリを使う

##C++
比較的開発環境整えやすい
各プラットフォームでのビルドを作ればランタイムが不要
GUIはちょっと大変。Qtとか使う。

##C#
Windowsでは開発ツールが入っている
Macでも開発できるが・・
クロスプラットフォームにするには Xamarinを使えばいいのだが・・
GUIを作るのが非常に楽

##Go
Windowsでは動かないコードもあり不満


#ツール
##Excel VBA
大抵の業務PCには入っている
Win、Mac両対応なので便利
でも 起動時間やムダが多いきがする

##UNITY
インストールが必要
プラットフォーム向けのビルドをすればインストール不要のはず
ただ　ツールのためにUNITY使うのは無駄が多い

#シェルスクリプト
##bashなりshなり
LinuxやMacではデフォルトで使える。
WindowsでもWSLなりGitbashなりで使える
ただ　プログラム言語としては使いにくいので
簡単な作業にかぎる

##コマンドプロンプト
Windowsには標準装備
Windows限定なので没

##パワーシェル
Windowsには標準装備
パワーシェルはLinux版もあるとかいうけど まず嫌がられるので没

#スクリプト言語
##生JavaScript
すべての環境で使える
ブラウザで実行するタイプのものだが、セキュリティなどで出来ないことがあるのでダメである

##Perl
Mac、Linuxでは標準装備
そろそろ終わりにしようか？

##PHP
Mac、Linuxでは標準装備
悪い選択肢ではない。使える人多いし。
個人的にはもう使いたくない

##node.js(JavaScript)
インストールが必要
みんなが知っている、みんなが覚える必要のある JavaScript
そして速度も速い
標準ライブラリの機能が少なくてnpmいっぱいしなければならない

##Python
Mac、Linuxでは標準装備
来ました本命！！　これで決定したい
2系か3系か？という問題もあるんだけど　スクリプトとしても完成度高いし
できればPythonにしたかった
ただし　1つだけ問題があった
それは　日本語化　多言語対応がちょっと弱いってこと

##Ruby
Mac、Linuxでは標準装備
というわけで　ファイナルアンサーです
最近のLinux系OSでは入っている言語
日本で作られた言語だけあって　日本語で問題がおこることが　ほぼない
業務支援としては　Rubyがベストという答えにいきつきました

#番外編
##Lua等
マイナーだし

##Haskell
ちょっとした要件をHaskellでかくのかっこいい
Fortranで何かを作りたい 没

##日課のネットサーフィンにて~

![スタート.png](https://qiita-image-store.s3.amazonaws.com/0/293790/0ccdfd32-8534-92a0-ed8a-39b3dbbb5575.png)
![やるぞ.png](https://qiita-image-store.s3.amazonaws.com/0/293790/b7b338b7-7587-7f91-980e-9f4ee165bbe6.png)

というわけで、Fortran90を使って人工無能の作成を目指します

※[偉大なるVIP](http://vipprog.net/wiki/prog_lang.html)

##設計
人工無脳の祖であるElizaを理想とします

必要なものを大まかに書き出すと、

>口のプログラム
>>受け答えを行う工程

>脳みそのプログラム
>>言われた言葉を吟味する工程
>>返答を考える工程

この三つの工程を実装する必要がありそう・・・ありそうじゃない？

無脳ないのに脳みそのプログラムとはこれいかに？

（　＾ω＾）・・・正直、無理難題じゃな

Fortranで自然言語処理ってできるん？みたいな状態です

何をどうすればいいのかすら手探りです

それでもやるんですけどネ！


##受け答えを行う工程

```Elisa.f90
implicit none
integer(8) i,c,n,m
character(140) L
character(140),allocatable :: W(:)
write(*,*) "My name is Elisa!"
write(*,*) "Please tell me various things!"
open(87, file='word.txt', form='formatted', status='old')
n=0
do
  read(87,'(A)',end=100)
  n=n+1
end do
100 close(87)
allocate (W(n))
read(*,'(A)') L
open(87, file='word.txt', form='formatted', status='old')
do i=1,n
   read(87,'(A)',end=200) W(i)
end do
200 close(87)
m=0
do i=1,n
   if (W(i)==L) then
       m=i
   end if
end do
if (0<m .and. m<=n) then
    write(*,*) "Don't make fun of me."
else
    open(87, file='word.txt', form='formatted', access='append')
    write(87,'(A)') L
    close(87)
    write(*,*) "I might try this time."
end if
end
```
やっていることは酷く単純です

格言を入力→テキスト内から格言を捜索して有無の確認→返答を行う

この人工無脳ちゃんの名前はElizaパイセンからあやかって『Elisa』にしました

とは言え、便宜上の名称なので他に良い名前があれば変えます

次にこのままでは、毎回毎回exeファイルを開かなければなりません

そのため、プログラムを任意のタイミングで終了させるようにします

```roop.f90
program Elisa
implicit none
integer(8) i,c,n,m
character(140) L
character(4) S
character(140),allocatable :: W(:)
write(*,*) "My name is Elisa!"
write(*,*) "Please tell me various things!"
S="next"
do while(S=="next")
open(87, file='word.txt', form='formatted', status='old')
n=0
do
  read(87,'(A)',end=100)
  n=n+1
end do
100 close(87)
allocate (W(n))
read(*,'(A)') L
open(87, file='word.txt', form='formatted', status='old')
do i=1,n
   read(87,'(A)',end=200) W(i)
end do
200 close(87)
m=0
do i=1,n
   if (W(i)==L) then
       m=i
   end if
end do
if (0<m .and. m<=n) then
    write(*,*) "Don't make fun of me."
else
    open(87, file='word.txt', form='formatted', access='append')
    write(87,'(A)') L
    close(87)
    write(*,*) "I might try this time."
end if
deallocate(W) !超重要
read(*,*) S
end do
end program
```
《while do》で挟んで《deallocate(W)》を添えただけです

最初《deallocate(W)》はなかったんですけど、Fortranは配列の上書きができないようで、

この文言が無いと二回目に突入する途中で配列を作成できない、と突っ返されます

これで簡単なオウム返しのプログラムの完成です

次は無限のサル定理やらマルコフ連鎖などを利用して文章を作成する工程を組んでいきたいと思います

以上！

##と、意気込んだものの
```
　 　　　*　　　　　　* 
　　＊　　無理です　　　＋　　 
　 　　 n ∧＿∧　n 
　＋　(ﾖ（* ´∀｀）E) 
　 　 　 Y 　　  Y　　　　＊
```
文節をざく切りにする方法をどう足掻いても思いつけなかったのでお蔵入りです

Fortranの不得意分野で戦おうとすればこうなるのは自明の理ですな・・・

大規模演算を利用した何か、が思いつくまでこの企画は没とします
Rubyの@_って何？？

## @_って何だろう...

gem等を読んでると、 `@_` を時々見るけど、`@`とは違うのかな？
と思い、調べてみました。

```.rb
    def config
      @_config ||= Config.new
    end
```

## 調査して来た
### ごく普通のインスタンス変数っぽい

- `@_hoge`はただのインスタンス変数
- `@hoge`でない理由はある命名規則に則っているからぽい

### ある命名規則とは？？

- 直接、このインスタンス変数を参照しないで欲しい!場合の規則

### どういう時に、インスタンス変数を参照しないで欲しい!となる？

- インスタンス変数を、ローカルキャッシュとして扱う場合!!

### 具体例
#### ローカルキャッシュとして扱いたい

```.rb
def notes
  @notes ||= Note.all
end
```

`notes`を実行すれば、Noteのデータを全て`@notes`に保持しておくことが出来、
`@notes`に何もない場合は、`Note.all`から取ってくることが出来る。

こういうのをローカルキャッシュという。

こういう場合は、`notes`で一貫して取って来て欲しいとなる。
つまり、他の箇所で、`@notes`や`Note.all`を使うより、`notes`を使って欲しい。

そうすれば、無駄にメソッドを実行することも無いし、何も無い場合は取得してくるように出来る。

```.rb
# こうじゃなく...
# @notesに何も無い場合は、nilになってしまう
def p_notes
  p @notes
end

# こうでもなく...
# 無駄にメソッドを実行してしまう
def p_notes
  p Note.all
end

# こう！
# @notesに何もなければ、Note.allで取得するし
# @notesに値がある場合は、その値を使ってくれる
def p_notes
  p notes
end

private

def notes
  @notes ||= Note.all
end
```

しかし、開発者たちはその意図が分かるだろうか??

毎回これは `notes`を使ってねと言わなければいけないのだろうか？

#### 直接使って欲しくない場合は、`_`を前に付ける

どうやら、Rubyを含む多くの言語にて、直接使って欲しくないような変数には、
`_`をプレフィックスとして付ける慣習があるみたいだ。

ということで、先ほどの`@notes`に`_`を付けてみると...??

`@_notes`　になる！

`@_`の正体は、こ、これか！！

```.rb
# @_notesは直接使わないで欲しいんだった!
# となりそう！
def p_notes
  p notes
end

private

def notes
  @_notes ||= Note.all
end
```

## 参考

- http://adarsh.io/use-an-underscore-when-memoizing-in-ruby/
- https://www.rubydoc.info/gems/rubocop/RuboCop/Cop/Naming/MemoizedInstanceVariableName
VSCodeでKotlinの実行環境を作る

# 環境
- OS: macOS Mojave
- エディタ: Visual Studio Code(以下VSCode)

# 作業手順

## kotlinをインストールします

```
$ brew update
$ brew install kotlin
```

## VSCodeの以下のプラグインをインストールします。

- [Kotlin Language](https://marketplace.visualstudio.com/items?itemName=mathiasfrohlich.Kotlin)
- [Code Runner](https://marketplace.visualstudio.com/items?itemName=formulahendry.code-runner)

## VSCodeのユーザ設定を変更します

[vscode-code-runner](https://github.com/formulahendry/vscode-code-runner) はデフォルトで`kotlinc`を使ってコンパイルしますが、これだとエラーが発生するので`kotlinc-jvm`を使うように変更します。

VSCodeのユーザ設定で、以下を追記してください。

```
    "code-runner.executorMap": {
        "kotlin": "cd $dir && kotlinc-jvm $fileName -include-runtime -d $fileNameWithoutExt.jar && java -jar $fileNameWithoutExt.jar"
    }
```

## Kotlinプログラムの実行

VSCodeでKotlinプログラムファイル(拡張子.kt)を作成し、右クリック > Run Code とすると、コードが実行されます。

<img width="622" alt="スクリーンショット 2018-11-22 20.16.16.png" src="https://qiita-image-store.s3.amazonaws.com/0/9875/bf12fd45-c9c3-8c7c-b18d-97292673da43.png">


# 参考

- [Programming with Kotlin in Visual Studio Code](https://medium.com/@agavatar/programming-with-kotlin-in-visual-studio-code-1d745d6b4ad1)
- [vscode-code-runner](https://github.com/formulahendry/vscode-code-runner)
Nextcloud のタグ機能

#はじめに
Nextcloud上のファイルを検索する場合に、日本語ファイル名の検索もできますが、日頃からきちんとファイル管理をしておけば、探す手間も省けます。Nextcloudではタグ付け機能がありますので、ファイルやフォルダにタグ付けをするのを紹介します。

#プラグイン
「Collaborative tags」です。標準でついています。
![画像112.png](https://qiita-image-store.s3.amazonaws.com/0/308127/6891a21e-c240-24be-2b91-5b2e2b2029fd.png)

#使い方
まずは管理者画面から。項目にワークフローがありますので、そこのコラボタグでタグの作成ができます。
![画像113.png](https://qiita-image-store.s3.amazonaws.com/0/308127/6be62b95-0ccd-9d8e-575d-43adff932fee.png)

タグの種類は、公開・制限付き・不可視の3種類があります。
・公開・・・全ユーザに見せる事も、割り当てする事もできる。
・制限付き・・・全ユーザに見せる事ができるが、割り当てする事ができない。
・不可視・・・ユーザーに見せる事も、割り当てする事もできない。（管理者が利用するのが目的）
![画像114.png](https://qiita-image-store.s3.amazonaws.com/0/308127/307d7283-7401-bd5e-399e-7b3632fe00c8.png)

次にユーザの画面です。対象フォルダやファイルの共有アイコンをクリックすると、右側に詳細設定画面がでますので、そこでタグ設定ができます。既存のタグを割り当てるか、ユーザ自身でもタグを作成する事ができます。（その際は公開タグとなります。）
![画像115.png](https://qiita-image-store.s3.amazonaws.com/0/308127/2fc8e892-dcdd-0532-7f1c-3f1b126447a5.png)

タグ検索です。画面左側のタグをクリックすると、タグを選択できます。
![画像116.png](https://qiita-image-store.s3.amazonaws.com/0/308127/bb9dfed7-1a77-b502-fae4-105429cbd8c4.png)

タグを選択すると、タグ付けされたファイルやフォルダが表示されます。
![画像117.png](https://qiita-image-store.s3.amazonaws.com/0/308127/e94f19d8-3bf4-2330-3ba9-ebedb58d1671.png)

#まとめ
今回は、タグの割り当てや検索について紹介しました。ファイルやフォルダにタグ付けをしておけば、ファイル管理も楽になるかと思います。このタグ付け機能とは別に、オートタギング機能というのがありますが、別の記事で紹介したいと思います。

この記事は、[スタイルズ社のNextcloudサイト](https://nextcloud.stylez.co.jp/nextcloudblog)にも公開しております。
Google Chromeはローカル環境でlinkタグのスタイルシートのcssRulesにアクセスできなかった

# テスト

Google Chromeのバージョン70.0.3538.110で2018/11/22にテスト。

## ローカル環境

```html
<html>
    <head>
        <style>
            body {
                color: red;
            }
        </style>
        <link rel="stylesheet" href="cssRule.css">
    </head>
    <body>aaa</body>
</html>
```

```css:cssRule.css
body{
    background: yellow;
}
```

このHTMLファイルとCSSファイルでテスト。

```text
> document.styleSheets[0].cssRules
CSSRuleList {0: CSSStyleRule, length: 1}
> document.styleSheets[1].cssRules
VM76:1 Uncaught DOMException: Failed to read the 'cssRules' property from 'CSSStyleSheet': Cannot access rules
    at <anonymous>:1:25
```

ローカル環境で外部リンクのcssRulesにアクセスすると例外が出た。

## サーバー環境

```
> document.styleSheets[0].cssRules
CSSRuleList {0: CSSStyleRule, length: 1}
> document.styleSheets[1].cssRules
CSSRuleList {0: CSSStyleRule, length: 1}
```
	
サーバーを立ててテストしたら、外部リンクのcssRulesにアクセスできた。

# 疑問

ローカル環境でHTMLファイルをGoogle Chromeで開いたら背景が黄色になったので、cssRule.cssのbackground: yellowを読んでいる。
しかし、ローカル環境でdocument.styleSheets[1].cssRulesにアクセスできないのは何故？
Cross-Origin Resource Sharing (CORS)ならブラウザの背景を黄色にしたらいかんでしょ。
Firefoxならローカル環境でcssRulesにアクセスできた。
遺伝子地図をfasta+gff3+Biopythonで作る Multi-FASTA対応版

2019/09/30
改良したスクリプトをgithubに上げました。
GeneHere; Gene position visulizer for GFF3
https://github.com/maedat/GeneHere


需要があるようなのでMulti-FASTAに対応したスクリプトを置いときます（forとかをいじった）

すっきり版のsingle-FASTAでいい人はこっち。
遺伝子地図をfasta+gff3+Biopythonで作る
https://qiita.com/MaedaTaro_Umiushi/items/b4243645ee07704dc84a



```python:multi-fasta.chrom.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-


#モジュールを読み込む
from reportlab.lib.units import cm
from Bio.Graphics import BasicChromosome
from Bio import SeqIO
from BCBio import GFF



#描画したい染色体の情報をリスト形式で入れる。該当するfastaファイルのパス、gffファイルのパス　を入れる
entries = [("OG1.fa", "OG1.pfam.gff3")]


max_len = 1000  
telomere_length = 0  

chr_diagram = BasicChromosome.Organism() 
chr_diagram.page_size = (100*cm, 30*cm)  

for index, (fasta_filename, gff_filename) in enumerate(entries):
	with open(fasta_filename, "rU") as fh:
		for record in SeqIO.parse(fh, "fasta"):
			features=[] #featuresを初期化しておく(無い時があるので）
			length = len(record) #配列長を取得する
			ID = record.id #配列名を取得する

#gffからfeatureを取得する。
			gff_handle = open(gff_filename)
			for rec in GFF.parse(gff_handle):
				if rec.id == ID:
					features = [f for f in rec.features ]
			cur_chromosome = BasicChromosome.Chromosome(ID)
			cur_chromosome.scale_num = max_len + 2 * telomere_length 

			# Add an opening telomere
			start = BasicChromosome.TelomereSegment() 
			start.scale = telomere_length
			cur_chromosome.add(start)

			#gffで得たfeature情報を追加する
			# Add a body - using bp as the scale length here.
			body = BasicChromosome.AnnotatedChromosomeSegment(length, features)
			body.scale = length 
			cur_chromosome.add(body)

		# Add a closing telomere
			end = BasicChromosome.TelomereSegment(inverted=True)
			end.scale = telomere_length
			cur_chromosome.add(end)

		# This chromosome is done
			chr_diagram.add(cur_chromosome)
		

chr_diagram.draw("simple_chrom.pdf", "TEST") 


```
Android StudioのProxy設定にハマったのでメモ

# 目的

会社内の認証ありProxyが設定されているネットワークで
GradleのProxy設定に酷くハマったのでメモ

# 現象

jcenter.bintray.com から.pomを取得しようとすると
407 Proxy Authentication Required が返却される。

# 対策
## 1. Android Studio の System Settings で設定

Android Studio のPreferenceから
Appearance & Behavior > System Settings > HTTP Proxy
で値を入力して設定。
しかし407 Proxy Authentication Required エラーが発生。

## 2. gradle.propertiesに設定

Android プロジェクト内のgradle.propertiesに以下を設定。
systemProp.https.proxyHost
systemProp.https.proxyPort
systemProp.https.proxyUser
systemProp.https.proxyPassword

しかしこれでも407 Proxy Authentication Required エラーが発生。

## 3. User/ユーザー名/.gradle のgradle.propertiesに設定

User/ユーザー名/.gradle にもgradle.propertiesが存在していたので、開いてみると
systemProp.https.proxyPasswordが空になっていた。

ここにパスワードを設定してGradle syncを実行すると無事syncに成功。

# 結果

Proxyこわい
beanのクラス名が重複したとき

コンパイルが通っても、実行時にエラーとなるため、重複しない名前をつけないといけない。１つ１つ手でつけると間違いが起こりやすいため、自動で付けるようにする。

##ルートパス直下等に名前付けクラスを定義

```FQCNBeanNameGenerator.java
public class FQCNBeanNameGenerator extends AnnotationBeanNameGenerator {

    @Override
    protected String buildDefaultBeanName(BeanDefinition definition) {
        return definition.getBeanClassName();
    }
}
```

##servlet-context.xmlを変更


```変更前：servlet-context.xml
	<context:component-scan base-package="jp.co.test" />
```

```変更後：servlet-context.xml
	<context:component-scan
		base-package="jp.co.test"
		 name-generator="jp.co.test.FQCNBeanNameGenerator" />
```

##参考

https://qiita.com/sinsengumi/items/655d9f3ff49646dfe61a
http://d.hatena.ne.jp/ocs/20101129/1291034951
Laravel でインデックスを作成、削除する

Laravelではデータベースの定義をマイグレーションを使って更新します。
最近、インデックスの作成や削除する際に、インデックス名の指定方法ではまりました。
ドキュメントをよく見ればわかるのですが、ここに注意点をまとめます。

ここに載せるサンプルコードは、マイグレーションファイル内に記述することを想定しています。

## 作成

### テーブル定義時に作成

```php
Schema::create('books', function (Blueprint $table) {
    $table->increments('id');
    $table->string('title')->index();  # Index
    $table->string('isbn')->unique();  # Create unique index
    $table->integer('price');
    $table->integer('author_id');
    $table->timestamps();
});
```

この例では2つのインデックスを作成しています。
テーブルのカラム定義の時に作成したインデックスの名前は、`${table_name}_${column_name}_${index_type}` のように自動で生成されます。
例えばこのサンプルコードだと、作成されるインデックスの名前はそれぞれ`books_title_index`と`books_isbn_unique`です。

`index`、`unique`メソッドの引数として文字列を渡すことで、インデックス名を指定することができます。

### テーブル定義後に作成

```php
Schema::table('books', function (Blueprint $table) {
    $table->index('title');
});
```

カラム名を指定することで作成できます。上と同様に、この時に作成されるインデックス名は`${table_name}_${column_name}_${index_type}`です。
第2引数に文字列を渡すことでインデックス名を指定できます。

#### 複合インデックス

```php
Schema::table('author_book', function (Blueprint $table) {
    $table->index(['author_id', 'book_id']);
});
```

複合インデックスは、インデックスの対象のカラム名を配列で指定することで作成できます。

## 削除

削除は、インデックスの種類ごとでメソッドが異なります。
通常のインデックスには`dropIndex`、ユニークインデックスには`dropUnique`を使います。

**:warning: 渡す引数の型によって削除する対象のインデックスが異なるで注意が必要です。**

### 文字列を渡した場合

指定した文字列と同じ名前のインデックスを削除する。
**:warning: カラム名では無いので注意**

```php
$table->dropIndex('books_title_index');
```

### 文字列の配列を渡した場合

先のインデックス名の生成ルールで作成したインデックス名を削除します。

```php
$table->dropIndex(['title']);
```

この例の場合、`books_title_index`という名前のインデックスを削除します。

複数の要素を持つ配列を渡した場合、その要素をカラム名とする複合インデックスを削除します。
複合インデックスの場合、配列で指定したカラムの順序がインデックス名にも影響するので、削除する際にもその順序を守る必要があります。

## まとめ

ドキュメントはよく読みましょう。

## 参考

* [Database: Migrations - Laravel - The PHP Framework For Web Artisans](https://laravel.com/docs/5.7/migrations#indexes)
【Tomcat8.5】HelloWorldアプリケーションをWebサーバにデプロイしてみる

#はじめに
EclipseでTomacatアプリケーション（HelloWorld）を作成し、warファイル化。
それをAWSに構築したWebサーバにscpでデプロイし、Chormeでページを表示させます。

#環境
Tomcat8.5
Apache2.4
pleiades4.8
macOS 10系

#やってみる
##Webサーバ構築
１年間無料の範疇でシンプルなEC2インスタンスを作成し、ApacheとTomcatをインストールします。
手順がわからない方は[私の過去記事](https://qiita.com/okome-chan/items/c4a62e67d54b0713c5a1)を参考にしてみてください。
ポート8080を空けていなかったためApacheのデフォルトページが表示されず難儀しました。。

##Eclipseのインストール
[こちらの記事](https://qiita.com/cypher256/items/233795f4fc58a704ee47)にありがたく倣います。
mac版だと日本語化が難しいとのことですのであっさり諦めます（）。

##Tomcatアプリケーションの作成
[こちらの記事](https://www.searchman.info/java_eclipse/1040.html)にありがたく倣って動的プロジェクトからコンパイルしたclassファイル、url-patternを明示したweb.xmlファイルを作成します。

他のページにTomcatのディレクトリ構成と仕様がバリッバリわかりやすく書かれています、
Tomcat難解すぎて嫌になっている方（私です）はぜひ一読してみてください。
もちろんこの構成が全てのTomcatアプリケーションに通ずる訳ではないですが、ロジックの触りが理解できると思います。

##Webサーバへデプロイ
先に構築したWebサーバにアプリケーションをデプロイします。
と言ってもWebサーバ上のTomcatフォルダ構成は上記サイトと同じですので、classファイルとweb.xmlファイルをターミナルからscpしてあげるだけです。
scpの手順がわからない方は[私の過去記事](https://qiita.com/okome-chan/items/2a0b85612176db55f605)を参考にしてみてください。

最終的に以下の配置になります。

```
/usr/tomcat8/webapps/searchman/WEB-INF/classes/HelloWorld.class

/usr/tomcat8/webapps/searchman/WEB-INF/web.xml
```

##tomcat.serviceの再起動、ブラウザ確認

Tomcatサービスが起動している場合は再起動、停止している場合は起動します。

```
・再起動
# systemctl restart tomcat.service

・起動
# systemctl start tomcat.service

・起動状態の確認（起動中か停止中か、ステータスがわからない場合はこのコマンドで確認します）
# systemctl status tomcat.service
```

あとはChromeで以下のURLを指定し、HelloWorldが表示されていればデプロイ完了です！

```
http://EIP:8080/searchman/servlet/hello
```

#おわりに
とにかく簡単なアプリでいいからAWS環境へのデプロイを体験したかったところ、[こちらの記事](https://www.searchman.info/java_eclipse/1040.html)に出会えました。本記事はこのサイトを布教するために書いたのが目的でもあります！w
私と同じような環境の方や、未経験者様のお役に立てますと幸いです。

#参考にしたサイト
[まずはここから！Javaの「Hello World」の書き方
](https://eng-entrance.com/java-hello-world)

[JAR,WAR,EARそれぞれの違いについて
](http://d.hatena.ne.jp/java-wizard/20140311/1394538929)

最後まで読んでいただきありがとうございました。
EC2にrootでsshする

## 目的
Ansibleのデバッグや検証でrootでsshしたかった。(ansible_ssh_user=root)
セキュリティホールになるので普通はadminやec2-userでsshして`sudo su -`するべし。

## やり方
ec2にrootでsshしようとすると怒られてしまうので

```
ssh -i "key.pem" root@ec2-55-190-222-191.ap-northeast-1.compute.amazonaws.com
Please login as the user "admin" rather than the user "root".

Connection to ec2-55-190-222-191.ap-northeast-1.compute.amazonaws.com closed.
```

rootにスイッチして`/root/.ssh/authorized_keys`を編集

```
admin@ip-172-13-10-8:~$ sudo su -
root@ip-172-13-10-8:~# cat /root/.ssh/authorized_keys
no-port-forwarding,no-agent-forwarding,no-X11-forwarding,command="echo 'Please login as the user \"admin\" rather than the user \"root\".';echo;sleep 10" 
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCZyYt7/aV7s+X7y3qzABJ6fFV3FitBr3NlDijEEuQT/aBA83L1fOKqjPxD41J0DVYt6yLO9Dmnce8ckXDy/2PM6DPwb8z65/8g5ITEwxq3mcTdmNDAul5zdLnfuDHeOeiEYhCaYetpHqf2gGo65ubVjQc8tl5NLkaX6l7NfUND/fuTxpPoYrhFK2SncdIyh4NUyR71yIWE1kxCTNCTBwMbC0Q5rP7n0Jyb/VPQW15LOdvXcWM7j3+k62uxcc8ZAg5FHdsHlY+qpDr3JYSAbJCew5a1YbbgNW4rqvkYUpooHZXRoYTOXN1a8FEv74kViSSI/zOrZoY2Vn6uKwZoel7H key
```

`ssh-rsa`以前のこの部分を削除

```
no-port-forwarding,no-agent-forwarding,no-X11-forwarding,command="echo 'Please login as the user \"admin\" rather than the user \"root\".';echo;sleep 10" 
```

こうなればOK

```
root@ip-172-13-10-8:~# cat /root/.ssh/authorized_keys
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCZyYt7/aV7s+X7y3qzABJ6fFV3FitBr3NlDijEEuQT/aBA83L1fOKqjPxD41J0DVYt6yLO9Dmnce8ckXDy/2PM6DPwb8z65/8g5ITEwxq3mcTdmNDAul5zdLnfuDHeOeiEYhCaYetpHqf2gGo65ubVjQc8tl5NLkaX6l7NfUND/fuTxpPoYrhFK2SncdIyh4NUyR71yIWE1kxCTNCTBwMbC0Q5rP7n0Jyb/VPQW15LOdvXcWM7j3+k62uxcc8ZAg5FHdsHlY+qpDr3JYSAbJCew5a1YbbgNW4rqvkYUpooHZXRoYTOXN1a8FEv74kViSSI/zOrZoY2Vn6uKwZoel7H key
```

以後rootでsshできるようになる

```
ssh -i "key.pem" root@ec2-55-190-222-191.ap-northeast-1.compute.amazonaws.com
Linux ip-172-13-10-8 4.9.0-8-amd64 #1 SMP Debian 4.9.130-2 (2018-10-27) x86_64

The programs included with the Debian GNU/Linux system are free software;
the exact distribution terms for each program are described in the
individual files in /usr/share/doc/*/copyright.

Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent
permitted by applicable law.
Last login: Thu Nov 22 10:16:13 2018 from 103.2.251.130
root@ip-172-13-10-8:~#
```
UIFont extension for the optimal fitting of text in a fixed size rectangle

Instead of fitting a layout object to contain a text label of fixed size, it is sometimes required to fit the text inside a fixed layout. 

In this particular case, we iteratively change the font until it converges on an optimized fit using the instantaneous aspect ratio of the label text. This helps to ensure the label fills the available space as much as possible.

```swift
extension UIFont {
    static func createFittedFont(maxWidth: CGFloat, maxHeight: CGFloat, text: String, fontName: String) -> UIFont? {
        
        let defaultSize: CGFloat = 20
        guard var font = UIFont(name: fontName, size: defaultSize) else {
            print("Error: invalid font name")
            return nil
        }
        
        let defaultWidth = text.width(withConstraintedHeight: CGFloat.greatestFiniteMagnitude, font: font)
        let defaultHeight = text.height(withConstrainedWidth: CGFloat.greatestFiniteMagnitude, font: font)
        let defaultAspectRatio = defaultHeight / defaultWidth
        let targetAspectRatio = maxHeight / maxWidth
        
        let eta: CGFloat = 0.03
        let coefficient: CGFloat = 0.4
        
        while (true) {
            let delta = (targetAspectRatio < defaultAspectRatio) ?
                maxHeight / text.height(
                    withConstrainedWidth: CGFloat.greatestFiniteMagnitude, 
                    font: font) - 1.0
                :
                maxWidth / text.width(
                    withConstraintedHeight: font.pointSize, 
                    font: font) - 1.0
            
            if(fabs(delta) <= eta) { break }
            let newSize = font.pointSize * (1.0 + coefficient * delta)
            font = font.withSize( newSize )
        }
        
        return font
    }
}```
javascript　~ 二次元配列のソート~

普通にsortメソッドを使ってて、そういえば二次元配列のsortとかどうするんだろって思ったのでまとめた。

**ここで言う二次元配列のsortとは特定の深さにある要素でsortする時を想定。**
# 普通の配列で昇順でsortするとき
```
var arr = [80, 40, 120];

arr.sort(function(a, b){
    return b - a;
});

=> [40, 80, 120]
```
これが普通のsortだけど二次元配列になった瞬間に10分ほどパニクった。
# 二次元配列の場合
```
var arr = [[6,2], [3,9], [1,7], [4,0], [8,5]]

array.sort(function(a,b){return(a[0] - b[0]);});

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

array配列のindex[1]を基準にsortしたければreturnするデータのindexを指定してあげるだけ。

以上！
A auto-fitting custom iOS toolbar with labelled buttons

In iOS 11+, it is possible to provide custom UIBarButtonItems to the Toolbar. The custom CustomToolbarButtonClass used in this example has a text label centered and directly below the button icon. 

The main challenge involves fitting the toolbar to its custom items. THe solution presented requires a subclass of the UIToolbar, which automatically fits the height of its items whenever there is a layout change. 

This solution is backwards compatible with iOS <11 versions. 

```swift
if #available(iOS 11.0, *) {
    let button =  CustomToolbarButtonClass(
        image: image,
        label: label,
        action: #selector(onButtonClicked(sender:)
    )
}
else {
    let button = UIBarButtonItem(
        image: image,
        style: .plain,
        target: self,
        action: #selector(onItemClicked(sender:)))
}
```

A custom toolbarClass which handles layout changes

```swift
class ToolbarClass: UIToolbar {
        
    var defaultHeight: CGFloat {
        get {
            return 44.0
        }
    }

    private var maxContentHeight: CGFloat? {
        get {
            return self.items?.map({ (button) -> CGFloat in
                (button as? ToolbarButtonClass)?.height ?? 0
            }).max()
        }
    }
    
    override func layoutSubviews() {
        super.layoutSubviews()
            
        if let contentHeight = self.maxContentHeight {
            var newFrame = self.frame
            newFrame.size.height = max(defaultHeight, contentHeight)
            if(self.frame != newFrame) {
                self.frame = newFrame
            }
        }
        
    }
    
    override func sizeThatFits(_ size: CGSize) -> CGSize {
        var size = super.sizeThatFits(size)
        if let contentHeight = self.maxContentHeight {
            let newHeight = max(defaultHeight, contentHeight)
            if(newHeight != size.height) {
                size.height = newHeight
            }
        }
        return size
    }
}
```
Create new iOS system UIImages by tinting any source image

Convert an image asset of any color to appear like a Apple system icon, with these easy extensions. Use icons with no transparent backgrounds for best results!

First, add the familiar "Apple blue" color

```swift
extension UIColor {

    class func rgb(r: Int, g: Int, b: Int, alpha: CGFloat) -> UIColor{
        return UIColor(
            red: CGFloat(r) / 255.0, 
            green: CGFloat(g) / 255.0, 
            blue: CGFloat(b) / 255.0, 
            alpha: alpha)
    }

    class func rgb(r: Int, g: Int, b: Int) -> UIColor{
        return self.rgb(r: r, g: g, b: b, alpha: 1.0)
    }

    class var appleBlue: UIColor {
        get {
            return UIColor.rgb(r: 0, g: 122, b: 255)
        }
    }
}
```

Then use it with this handy tint extension

```swift
extension UIImage {

    func tint(with color: UIColor) -> UIImage
    {
        UIGraphicsBeginImageContext(self.size)
        guard let context = UIGraphicsGetCurrentContext() else { return self }
        context.scaleBy(x: 1.0, y: -1.0)
        context.translateBy(x: 0.0, y: -self.size.height)
        context.setBlendMode(.multiply)
        
        let rect = CGRect(x: 0, y: 0, width: self.size.width, height: self.size.height)
        context.clip(to: rect, mask: self.cgImage!)
        color.setFill()
        context.fill(rect)
        guard let newImage = UIGraphicsGetImageFromCurrentImageContext() else { return self }
        UIGraphicsEndImageContext()
        return newImage
    }  
}
```
PHPビルトインウェブサーバーで簡易Webサーバを立てる

* 以前教えてもらったのにコマンドを忘れてたのでメモしておく。

## 目的
* ローカル環境に簡易Webサーバを立てて、HTMLとかJSの動作確認をさくっとしたい

## PHPビルトインウェブサーバを使うメリット
* apache, nginx, xampp, mampを準備しなくてもPHPさえ入っていればコマンド一発で起動できる。

## 使い方
* ドキュメントルートにしたいディレクトリに移動して下記コマンドを実行

```
$ php -S localhost:8000
```

* ブラウザで「http://localhost:8000」にアクセスする

## 参照
* ビルトインウェブサーバー https://secure.php.net/manual/ja/features.commandline.webserver.php
Measure multiple Fragment/View sizes with Kotlin coroutines

In a complex layout in Android, we need the size of multiple fragments/views. However, in a dynamic layout, these sizes may be changing frequently, and thus we must measure them when they are required. 

This measurement cannot always be calculated immediately. For example, if a fragment view has just been created, getLeft()/getTop() etc. will return 0 because the view has no intrinsic size yet. We must therefore post a runnable, or assign a layoutListener, with a callback that returns the fragment size once it is known.

If we require the size of multiple fragments/views, our calling function must wait for all sizes to be returned before it can continue. In Kotlin, coroutines are a useful method of doing this. 

This is our calling function, which waits for the result of multiple height measurements. It will return a list of heights in a completion handler.

```swift
override fun updateHeights(completion: (List<Int>) -> Unit)  {
    val job = launch {

    	// "fragments" is a predefined list of CustomFragment type
        val deferred = fragments.map { fragment ->
            async(CommonPool) { fragment.computeHeight() }
        }
        completion(deferred.map { it.await() })
    }
}
```

This is our customFragment with a suspend function and continuation return value

```swift
class CustomFragment: Fragment {

	open suspend fun computeHeight() : Int = suspendCoroutine { continuation ->

		//call your measuring method with a callback that returns the result
		this.measureHeight({ size ->
			continuation.resume(size.height)
		})			
	}
} 
```
rspecのletで定義した変数をbeforeで変更するときの注意

rspecのletで定義した変数をbeforeで変更しても、思ったようには行かないよという話です。

```ruby:akiyah_spec.rb
# frozen_string_literal: true

require "rails_helper"

describe "Akiyah" do
  let(:int) { 123 }
  let(:str) { "abc" }
  let(:arr) { ["a", "b", "c"] }
  before do
    int = 456
    str = "def"
    arr[0] = "x"
    arr = ["d", "e", "f"]
    arr[1] = "y"
  end
  it { expect(int).to eq 123 }
  it { expect(str).to eq "abc" }
  it { expect(arr).to eq ["x", "b", "c"] }
end
```

letで宣言した変数をbefore内で=で代入しても、itの中では変わっていません。
beforeの中で(あとで使えない)新しい別の変数を作っているだけなんですね。

Array(やHash)の場合に、その中の要素を置き換えている場合は、itの中でも反映されます。

意外にこういう状況にはならないので、あんまり問題にはならないのですが、この前モブプロしているときに遭遇したので書いておきました。

# コメントで解説していただいたので追記

letで定義しているのは変数ではなくてメソッドなのだと理解すれば、上のようなコードをみても誤解は減りそうです。
`変数` みたいに見えるものを `メソッド` の呼び出しだとわかるように変えてみました。

```ruby:akiyah_spec.rb
# frozen_string_literal: true

require "rails_helper"

describe "Akiyah" do
  let(:int) { 123 }
  let(:str) { "abc" }
  let(:arr) { ["a", "b", "c"] }
  before do
    int = 456
    str = "def"
    arr()[0] = "x"
    arr = ["d", "e", "f"]
    arr[1] = "y"
    p arr #=> ["d", "y", "f"]
  end
  it { expect(int()).to eq 123 }
  it { expect(str()).to eq "abc" }
  it { expect(arr()).to eq ["x", "b", "c"] }
end
```

beforeで `arr()[0] = "x"` をすると、 `arr()` の結果が変更されるのは面白いですね。コメントで書いていただいたように、letで定義したメソッドは戻り値を保存しておくからこうなるのですね。