OmniAICreator/Qiita-1.07M huggingface dataset:
Vivado HLS > v2019.1 > memory copy is not supported unless used on bus interface possible > v2016.2:問題なし

```txt:動作環境
PYNQ-Z1
Windows 10 Pro v1909
Vivado HLS v2019.1
```

### 概要

- Vivado HLSでmemcpy()を使った実装でエラーが出る
    - Vivado HLS v2019.1
- Vivado HLS v2016.2では出なかったエラー

### 症状

- FPGA プログラミング大全 Xilinx編 (小林優様)
    - 10-4 AXIマスターの描画回路を設計

fillbox.cおよびfillbox_tb.cを用いてHLSでRun C SimulationとRun C Synthesisを行った。

- Run C Simulation : 成功
- Run C Synthesis: エラー (下記)

![スクリーンショット 2020-09-15 201048.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32870/81eb6625-9bc7-4b9a-5218-3d50d0ffb505.png)

## エラー

### エラー1 > ERROR: [HLS 200-70] Synthesizability check failed.

```
ERROR: [HLS 200-70] Synthesizability check failed.

command 'ap_source' returned error code

    while executing

"source C:/ip_200902/fillbox_2019_1_3/fillbox/solution1/csynth.tcl"

    invoked from within

"hls::main C:/ip_200902/fillbox_2019_1_3/fillbox/solution1/csynth.tcl"

    ("uplevel" body line 1)

    invoked from within

"uplevel 1 hls::main {*}$args"

    (procedure "hls_proc" line 5)

    invoked from within

"hls_proc $argv"  fillbox:solution1  2020/09/15 20:10:12
```


### エラー2 > memory copy is not supported unless used on bus interface possible 

```
ERROR: [SYNCHK 200-22] ../fillbox_ip/SRC/fillbox.c:32: memory copy is not supported unless used on bus interface possible 
cause(s): non-static/non-constant local array with initialization).   fillbox:solution1  2020/09/15 20:10:12
```

### エラー3 > unsupported memory access on variable 'vram' which is (or contains) an array with unknown size at compile time.


```
ERROR: [SYNCHK 200-61] ../fillbox_ip/SRC/fillbox.c:31: unsupported memory access on variable 'vram' which is (or 
contains) an array with unknown size at compile time.   fillbox:solution1  2020/09/15 20:10:12
```


### v2016.2 > 問題なし

本の掲載時はv2016.2が使われていたようだ。
試しにv2016.2にしたところ、上記のエラーは出なくなった。

Vivadoのバージョンアップ時に上記のチェックを厳しくしたのだろうか。

### 関連

- [xf_warpperspective (or warpaffine) do not synthesize](https://github.com/Xilinx/xfopencv/issues/41)


書いていることを理解するまでは学習が進んでいない。


### 組み合わせ

- Vivado HLS v2016.2
    - fillbox IPの作成
- Vivado v2019.1
    - bitstream作成
- XSDK v2019.1
    - アプリ作成

上記の組み合わせで高位合成fillboxの実装を確認できた.

![スクリーンショット 2020-09-15 211440.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32870/b44b33f1-fcc9-c3f1-ddea-7fb4290c2727.png)


![a2e6cd8c01f7e391.jpeg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32870/0fe46424-08c7-1bf3-f845-5b621338da3d.jpeg)
webpackerのしくみ

# webpackerについて
前回webpackerをインストールする際、こんな記事を書きました。
[Webpackerとは (Rails6で rails s してエラーが出た時の話)](https://qiita.com/nideratakumin/items/dda8cabc431ed6d6ee8c)

# webpackerの構成
webpackerのインストールで生成されたディレクトリapp/javascript/packsの中に
application.jsというファイルが作成されます。
webpackerはapp/javascript/packsディレクトリにあるファイルをエントリポイントとしてコンパイルを実行します。
それ以外のjsファイルはapp/javascript配下の他のディレクトリに置き、app/javascript/packs/application.jsから読み込みます。

(※エントリポイント・・・コンピュータプログラムを実行する際に、一番最初に実行することになっている箇所のこと。ここでは "コンパイルを開始するファイル" の意味。)

例:

app/
　├ javascript/
　│　└channels/
　│　└ packs/
　│　　　└ application.js (エントリポイント)
　└ example/
　　　└ example.js

```app/javascript/packs/application.js
// デフォルトの記述
require("@rails/ujs").start()
require("turbolinks").start()
require("@rails/activestorage").start()
require("channels")

// example.jsを読み込む
import '../example/example'
```


app/views/layouts/application.htmlに下記を記述することで、コンパイルしたjavascriptをビューで読み込むことができます。

```app/views/layouts/application.html.slim
// slimの場合
= javascript_pack_tag 'application'

// ERBの場合
<%= javascript_pack_tag 'application' %>
```

# もうちょっと詳しく
加筆予定です。
RailsアプリにReactを導入してみようと思います。
Xamarin.Formsでボタン押下時に表示を変更

# やること

ボタンを押すと、テキストが変わり押せなくなるようにします。

# コード


```xml:xaml抜粋
<Button Text="Press me" Pressed="OnPressed" />
```


senderに代入します。バインディングより幾分か楽です。

```c#:cs抜粋
public partial class SamplePage : ContentPage
{
    public SamplePage()
    {
        InitializeComponent();
    }

    void OnPressed(object sender, EventArgs args)
    {
        (sender as Button).Text = "pressed";
        (sender as Button).IsEnabled = false;
    }
}
```
WindowsにUbuntuを入れてGPGPUを使用する

WindowsにUbuntuを入れてGPGPUを使用する

以下３つが必要
・WSL2
・Windows Insider Programのdevチャンネルの購読
・NvidiaDriverのバージョンを最新に

````
sudo apt-key adv --fetch-keys http://developer.download.nvidia.com/compute/cuda/repos/ubuntu2004/x86_64/7fa2af80.pub
sudo sh -c 'echo "deb http://developer.download.nvidia.com/compute/cuda/repos/ubuntu2004/x86_64 /" > /etc/apt/sources.list.d/cuda.list'
sudo apt-get update
sudo apt-get install -y cuda-toolkit-11-0
````

ちょっと最近のWindowsUpdateでWSLが使えなくなるバグがあるので、そういうのに会ったら、回復で前回のバージョンに戻すを使用

以下は参考リンク

windows:wsl:trouble_shooting [ともやん・どっと・ねっと] 
https://www.tomoyan.net/windows/wsl/trouble_shooting

NVIDIAドライバダウンロード 
https://www.nvidia.co.jp/Download/index.aspx?lang=jp

Windows Subsystem for Linux 2(WSL 2)をセットアップしてみた | Developers.IO 
https://dev.classmethod.jp/articles/how-to-setup-wsl2/

待ってました CUDA on WSL2 - Qiita 
https://qiita.com/ksasaki/items/ee864abd74f95fea1efa

WSL2 にしたいのにエラーが出る問題 - Qiita 
https://qiita.com/saida/items/ab6c5a980a1f5383c23a
【Java開発】第2回 演算子

#はじめに

皆さん。こんにちは！

DreamHanksの254cmです。

今回は演算子について説明していきます。

Java記事のまとめは[こちら](https://qiita.com/DreamHanks/items/6b1996e1f8ed66bbd456)です。

前回の記事は[【Java開発】第1回 変数](https://qiita.com/drafts/e06b036ddadfef2cfeca/edit)です。

##演算子
Javaでは色んな演算を対応するために多様な演算子を提供しています。

Javaが提供する演算子は下記のようになります。

1. 増減演算子
2. 算術演算子
3. シフト演算子
4. ビート演算子
5. 比較演算子
6. 論理演算子
7. 条件演算子
8. 代入演算子
9. instanceof演算子


各演算子について学びましょう。

※演算は式を計算して結果を出す過程を演算と呼びます。

##演算子の種類

###・増減演算子
増減演算子は演算される変数の値に1を足したり引きたりする演算子です。

ただし、演算子が付けられる位置によって増減されるタイミングが変わります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/3d451e18-2821-9b12-1bab-6771b078c284.png)


###・算術演算子

数学の四則演算と同様なものですが、残り算というものがもう一つあります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/19f0a6ae-3e69-3d9c-5946-ef8e4ecaef89.png)

※残り算とは？

対象の値を割ってからの残りを出す演算です。

例）8 % 3 = 2
　　8 % 10 = 8 

###・シフト演算子

シフト演算子は演算される値を2進数のビート単位で展開してその2進数のビートの桁を移動させる演算子です。

ビートの話は2進数を扱う記事でもっと詳しく扱います。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/e07c5daf-f18c-0ad9-5749-164e13bfe025.png)												

例）

```java

int value = 13;
value = value << 1;
System.out.println(value); // 26
```

2行目でvalueの値を左に1桁移動させています。

その動作を2進数で考えてみると

13は2進数で展開しると

１１０１

です。

この2進数の桁を左に移動させると

１１０１０

になってvalueの値は26になります。

###・ビート演算子

ビート演算子は対象になる値を2進数で展開して各桁数を比較した結果を出す演算子です。

各演算子の説明は下記のようになります。

* **&演算**

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/62f6516e-9e81-6212-7a8b-8e6c823f292c.png)

対象１ビートと対象２のビートの中で、二つ全部値が１になっている桁に1を出します。

なので1番目と5番目の桁には１が出されます。

* **|演算**

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/38ab9235-c260-7e89-113b-0720e3a65a4c.png)

対象１ビートと対象２のビートの中で、一つでも１になっている桁に１を出します。

なので1番、2番、3番、5番目の桁に1が出されます。

* **^演算**

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/1812209c-876a-5cad-0165-c96d83ad7838.png)

対象１ビートと対象２のビートの中で、一つだけ１になっている桁に１を出します。

なので2番と3番目の桁に1が出されます。

* **~演算**

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/b96a2583-4d42-c1b7-12b0-c400725e8e5e.png)

各ビートの数を反転させます。

なのですべての桁の値が反転され、結果が-20になります。

###・比較演算子

比較演算子は二つの式または値を比較してその結果としてtrueまたはfalseを出す演算子です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/7c3675ba-feb3-5490-a837-86a2e10059db.png)

###・論理演算子

論理演算子はいくつかのboolean値または比較式の結果を集めてtrueかfalseかを出す演算子です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/db458abf-29ee-770f-8ef2-7760262bcda4.png)																		

###・条件演算子(三項演算子)

条件演算子は条件式の結果によって行う処理が異ならせる演算子です。

* **書き方**

```java

条件式 ? 処理1 : 処理2
```

上記の条件式の結果がtrueの場合、処理1が実行され、falseの場合には処理2が実行されます。


###・代入演算子
代入演算子は変数に値を代入させる演算子です。

代入演算子は算術演算子、ビート演算子、シフト演算子と組み合わせて使えます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/708649/433ee10d-a8d0-fc07-d52d-505a0d2cc6cc.png)

#終わりに

今回の記事は以上になります。

次回はJavaの[条件分岐](https://qiita.com/DreamHanks/items/45b1df7ba96f3bbe2209)を学びましょう。

私たちの最新の記事は[こちら](http://blog.dreamhanks.com/java%e5%85%a5%e9%96%80%e8%ac%9b%e5%ba%a7/)で確認することができます。

ご覧いただきありがとうございます。
【Ruby】FizzBuzz問題

# 内容

1~100までの数字をターミナルに出力し、3の倍数の時は数字の代わりに文字列でFizz、5の倍数の時はBuzz、両方の倍数である15の倍数の時はFizzBuzzと出力されるプログラムを作ってねという問題について解説を載せて書いてみる。

# 答え

```ruby
def fizz_buzz
  num = 1
  while (num <= 100) do
    if (num % 3 == 0) && (num % 5 == 0)
      puts "FizzBuzz"
    elsif (num % 3) == 0
      puts "Fizz"
    elsif (num % 5) == 0
      puts "Buzz"
    else
      puts num
    end

    num = num + 1
  end
end


fizz_buzz
```

# 解説

変数numに1を代入し、whileメソッドでnumが100以下の時、3の倍数かつ5の倍数の時にFizzBuzzと出力。3の倍数の時にFizzと出力。5の倍数の時Buzzと出力。それ以外はnumを出力し、最後にnumに1を追加する。
Git プルリクで他の人のコミットが含まれていた

間違っていたらコメントください
##状況
プルリクを出そうとした時に、commit履歴に他の人のcommitが含まれていた。
##環境
**マージ先のブランチ**
・develop
**自分が作業しているリモートブランチ**
・feature
**自分が作業しているローカルブランチ**
・feature

##解決
**コマンドの流れ**

```
$ git log
$ git rebase -i コミットID
  不要なコミットの削除
$ git rebase origin/feature
$ git push -f origin feature 
```
##解説
消したいcommitIDを確認する

```
$ git log
```

消したいcommitの直前のIDを利用することで削除できる

```
$ git rebase -i コミットID
```
〜〜〜コミットを削除する〜〜〜

自分が作業していたローカルブランチに自分が変更したcommitだけくっつける

```
$ git rebase origin/feature
```

作業中のリモートブランチに正しいものを適用

```
$ git push -f origin feature
```
【初心者でもわかる】PCとスマホで表示非表示を切り換える共通CSSを作ると効率UP！

# どうも7noteです。レスポンシブで表示非表示を切り換える簡単な方法。

どうも7noteです。
この記事は以下へ引っ越しました。

https://naruweb.com/coding/responsive-css/
俺でもわかるActiveDirectory Group属性 Info(説明)を変更したいPowerShellコマンドレット

俺です。

# グループの説明を変えたい

このようなグループがあり、info(Notes, 説明)を変えたいと思ったとします。

```
PS C:\Windows\system32> Get-ADGroup group -Properties info


DistinguishedName : CN=group,OU=sandbox,DC=saikou,DC=jp
GroupCategory     : Security
GroupScope        : Global
info              : unko
Name              : group
ObjectClass       : group
ObjectGUID        : XXXXX-XXXXX-XXXXX-XXXXX-XXXXX
SamAccountName    : group
SID               : XXXXX-XXXXX-XXXXX-XXXXX-XXXXX
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/42755/63ad0ea9-0c1d-920d-cdab-80c921dc76d3.png)

# Set-ADGroup -Replaceを使う

はい無事漏れました！

```
PS C:\Windows\system32> Set-ADGroup -Identity "CN=group,OU=sandbox,DC=saikou,DC=jp" -Replace @{Info="buriburi"}
PS C:\Windows\system32> Get-ADGroup group -Properties info


DistinguishedName : CN=group,OU=sandbox,DC=corp,DC=andgate,DC=co,DC=jp
GroupCategory     : Security
GroupScope        : Global
info              : buriburi
Name              : group
ObjectClass       : group
ObjectGUID        : XXXXX-XXXXX-XXXXX-XXXXX-XXXXX
SamAccountName    : group
SID               : XXXXX-XXXXX-XXXXX-XXXXX-XXXXX
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/42755/d466b32a-d742-63a7-4de7-0d56e7790af2.png)

トイレは2回流そう！な！

完
Juniper EX / QFX で存在しているはずのポートが見えない時に読んでください

# 症状
概要running JunosなスイッチであるはずのIFが見えない。
## 検証環境
筐体： EX3300-24T
OS: Junos 12.3R9.4

## 症状の例
物理的についてるはずのポートがCLIから見えない...! 

```
root> show interfaces xe-0/1/2
error: device xe-0/1/2 not found
```

# 切り分け

## 1. モジュールが刺さってない
SFPモジュール/DACなどが何も刺さってない場合、`not found`になる。

## 2. vc-portに指定されている
Junosのスイッチは複数のスイッチ筐体を論理的に1台に見せる"virtual chassis"機能があり、その専用リンクとして当該IFが指定されている場合がある。
### 確認方法
vc-portに指定されているポートを見るコマンドは以下の通り。

```
root> show virtual-chassis vc-port
fpc0:
--------------------------------------------------------------------------
Interface   Type              Trunk  Status       Speed        Neighbor
or                             ID                 (mbps)       ID  Interface
PIC / Port
1/3         Configured               Absent
```

### 直し方
`request`コマンドでvc-portから外す。 
例えば`xe-0/1/3`にあたるポートをvc-portから外す場合は下記のようになる。

```
root> request virtual-chassis vc-port delete pic-slot 1 port 3
```

逆にvc-portに新しくポートを割り当てる場合は以下のようになる。

```
root> request virtual-chassis vc-port delete pic-slot 1 port 2
```

## 参考
[[EX/QFX] Physical Interface is not listed in 'show interface' command output](https://kb.juniper.net/InfoCenter/index?page=content&id=KB22218)
SQL Server: パフォーマンスモニタの情報をダンプする仕組みの作り方

# 概要
パフォーマンスモニタでSQL Serverの各種情報を取得してアセスメントしたい場合があると思います。
都度設定するのも面倒なので、テンプレートファイルを作成しました。

# 設定したテンプレートの概要
- 毎日15時に取得開始
- 23時間50分後に取得終了（24時間後だと、次の開始と処理がかぶってうまくいかない場合があるため）
- 10日間分ファイルを保存。古いファイルは自動削除
- 取得するメトリクスリストは以下の通り

```
\Memory\*
\Network Interface(*)\*
\Server\Bytes Received/sec
\SQLServer:Access Methods\*
\SQLServer:Buffer Manager\*
\SQLServer:Buffer Node(*)\*
\SQLServer:General Statistics\*
\SQLServer:Latches\*
\SQLServer:Memory Manager\*
\SQLServer:Resource Pool Stats(*)\*
\SQLServer:SQL Statistics\*
\SQLServer:Wait Statistics(*)\*
\SQLServer:Workload Group Stats(*)\*
\System\*
\LogicalDisk(*)\*
\PhysicalDisk(*)\*
\Process(*)\*
\Processor(*)\*
\SQLServer:Databases(*)\*
\SQLServer:Locks(*)\*
\SQLServer:Plan Cache(*)\*
\SQLServer:SQL Errors(*)\*
\SQLServer:Batch Resp Statistics(*)\*
\Distributed Transaction Coordinator(*)\*
\SQLServer:Exec Statistics(*)\*
\SQLServer:Transactions\*
\SQLServer:Replication Dist.(*)\*
\SQLServer:Replication Logreader(*)\*
```

# テンプレートの設定手順
#### 1. テンプレートファイルをダウンロードし、サーバーに配置
テンプレートファイルは[こちら](https://github.com/masaki-hirose/SQLServer-Info/blob/master/DMV%E3%83%80%E3%83%B3%E3%83%97/perfmon_template.xml)

#### 2. パフォーマンスモニターを開く
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/c797d8b5-5242-1436-c06d-b1947e826357.png)
[ユーザー定義]を右クリックして[新規作成]-[データコレクターセット]を選択

#### 3. 名前を適当に入力して[次へ]
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/bf9b7705-977a-5ebc-1c6f-1348194bb016.png)

#### 4. [参照]を押す
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/75ef37a9-98fa-7ef7-b578-4600d4d81492.png)

設置したテンプレートファイルを選択して[次へ]

#### 5. データの保存場所を選択して[完了]を押す
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/571f2270-ef31-a854-b4ad-088666ee240a.png)

以上で作成は完了です。
毎日15時に自動で取得開始します。

保存先ディレクトリにいくと「DataCollector01」というファイルが生成されているため、開くと各メトリクスが波形で表示されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/ebbcfaa1-c8a2-02e8-a6ca-a3bfd4e916c1.png)

あとはみたい値だけ絞り込んだり、さらにCSVファイルとしてダンプしたりすればOKです。

# 注意点
1日あたりだいたい1.5GBくらいのファイルサイズとなるため、合計15GB～20GBくらいの容量を使う、という認識のもと設定してください。
条件式で注意したいこと

【概要】
----------------------------------------
<b>1.結論</b>

<b>2.具体例</b>




1.結論
----------------------------------------
上から読み込まれるので<b>書く順番に気をつける！</b>
<br>

2.具体例
----------------------------------------
たとえば、以下の３つの条件を基に出力するプログラムを記載する場合を見てみます。

❶20以下であれば"20以下の数字"と出力
❷20より大きい数字であれば"20より大きい数字"と出力
❸20以下で0以下であれば"0以下の数字"と出力

この場合で以下の記載をしています。

```ruby
int = gets.to_i

if int <= 20
  puts "20以下の数字" #❶
elsif int <= 0
  puts "0以下の数字" #❷
else
  puts "20より大きい数字" #❸
end

```

この場合、int に"-1"と記載すると❶の

```ruby
if int <= 20
  puts "20以下の数字"
```
が反応してしまい、本来出したい❷の出力がされません。
これはプログラムは上から下に順番に読み込まれるためです。(defはあとから読み込み、javascriptの関数宣言は先に読み込まれるといった例外はあります。)

なので❶と❷の順番を入れ替えて

```ruby
int = gets.to_i

if int <= 0
  puts "0以下の数字" #❶
elsif int <= 20
  puts "20以下の数字"  #❷
else
  puts "20より大きい数字" #❸
end
```
とすると本来の意図を汲み取ったプログラムになります。
<br>
【UFT】ユーティリティまとめ　～画像比較～

テスト自動化ツールである、UFT(Unified Functional Testing)

今回は UFTでの画像比較について、
公式リファレンスを参考にしながら使い方などをまとめたいと思います。

※公式リファレンスは英語のみです。日本語記事がないので、作成をしてみました。

# 画像比較（BitmapCheckPoint）
画像比較にはBitmapCheckPointを使用して実装します。
下記に手順とサンプルコードを記述しますので参考にしてみてください。


```VB:画像比較
'+++++++++++++++++++++++++++++++++++++++++++++++++++++++++
' Method		： CheckPoint
' Description	： オブジェクトリポジトリにBitmapCheckPointを登録し画像比較する
' example		： hoge.Check ckeckpoint("name")
'+++++++++++++++++++++++++++++++++++++++++++++++++++++++++

' 手順１．記録（F6）を押下。記録モードを起動させる。
' 手順２．ツールバー右側にある「虫眼鏡」のアイコンを押下。
' 手順３．リストから「ビットマップチェックポイント」を押下
' 手順４．画像比較したい画像ないしオブジェクトをクリック
' 手順５．[ビットマップチェックポイント]ダイアログが表示されるので、取得対象を選択しOKを押下
' 手順６．[ビットマップチェックポイントのプロパティ]が表示されるので、下記の項目を確認しOKを押下
'	・名前　に任意の名称を付ける
'	・選択領域と実行時のビットアップを比較する　にチェック
'	・画像が正しいことを確認する（領域選択可能）
' 手順７．Action内にコードが生成されるので確認する（下記のようなコードが表示されます）

' 手順４で選択したbitmapが存在するか10秒間探す。なければFailedとなる。
WpfWindow("Micro Focus MyFlight Sample").WpfImage("image2").Check CheckPoint("image2")
```

# Insight Objectを使った画像比較（非推奨）
## Insight Objectの説明
UFTでは、テスト対象の画面上の要素（オブジェクト）を**オブジェクトリポジトリ**に登録し、オブジェクトを使って自動操作を行います。
しかしテスト対象によっては画面上の要素（オブジェクト）が取得できない場合があります。
そういった場合にUFTでは画面上に表示されている情報（画像）を要素（オブジェクト）として登録・使用することができる**Insight**という機能があります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/288745/64287e4c-eefb-d906-86ee-6410a8e67b8b.png)

## Insight Objectを使った画像比較の実装方法
Insight Objectは本来、画面上の要素（オブジェクト）が取得できない場合に要素を画像として扱い自動化を実現する機能です。
そのため画像比較として使うことを筆者としては推奨いたしません。
しかし「Insightを使って画像比較をしたい」という人や実際に画像比較を用いてテストをしている現場もあることもあることから、実装方法について簡単に解説をいたします。

なおここで説明する画像比較は以下のテストケースを想定しています。
「Insight Objectに登録されている画像が表示されているかどうか」
1.比較対象の画像をInsight Objectとしてオブジェクトリポジトリに登録する
2.VBScriptのif文を使い、画像が表示されているのかをExistsメソッドを使い確認する

```VB:画像比較

' ■ 画像が表示されているかを確認する
'Insight Objectで取得した画像が存在するか10秒間探し、表示されていなかったらレポートにエラーを出す。
if hoge.InsightObject("画像").Exists(10) Then
    Reporter.ReportEvent micPass ,  "Pass"  , "画像が表示されていることを確認"
Else
    Reporter.ReportEvent micFail ,  "Fail"  , "画像が表示されていません"
End If
```




# おわりに
UFTに同梱されているサンプルアプリケーションを使いデモ動画を作成しました。
上述した手順に沿って動画を作成をしているので参考にしてみてください。

|OS|Windows 10|
|---|---|
|UFT|Ver.15.01|
|システム|Flight GUI|

![BitmapCheckPoint_3.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/288745/4ea2c842-bb55-de61-c048-db061a92da9a.gif)


# 参考
・Bitmap checkpoints
https://admhelp.microfocus.com/uft/en/15.0-15.0.1/UFT_Help/Content/User_Guide/About_Checking_Bitmaps.htm
【感想】TechCampを受講してみて

約2ヶ月半のTechCampを卒業して、今後受講を検討している方の参考になればと思い、感想を述べます
誤解のないように申し上げると、上から目線で評論するつもりもなく、批判するつもりもないです。

まず私としては短期集中型の受講料65万円という価格ほどの価値はなかったと感じてます。
価値としては40万円程かなと。

理由とコメントを述べると、
・教材が基礎に毛が生えたレベル（それでも未経験者にとっては難しいです）
・Udemyや書籍など他の教材で学習できる（自学ができない人は受講の価値あり）
・質問し放題と謳ってはいるが、割と早々に質問するまでのハードルが上がる（正しい質問の仕方を学ぶチャンスではあるが、質問フォーマットを正確に作るためと、メンターと通話が繋がるまでに1〜2学習できるぐらいの時間がとられる）
・メンターの質のレンジが広い（ほとんどが良いメンター様でしたが、さっさと終わらせようという空気を出してくるメンターもいる）
・日々のスケジュールに沿って行動することでトータルで効率のいい1日を送ることができる（ただし人による。私は自分のペースが崩れると一気に集中力が落ちるので中盤以降はチームメイト了承の上、自分のペースでやってました）
・カリキュラム外の質問には答えてもらえない（特に自作アプリ以降は質問に答えてもらえません。本当はここでたくさんのことを教わりたかった）
・毎日解くRubyの問題が面白い（Paizaのようなものです。私のようなクイズ好きだと楽しいです）
・ライフコーチのホスピタリティが高い（改善点は促しつつも、非常に上手に自信とモチベーションを上げてくれる）
・キャリアアドバイザーから得られる情報の8割方がネットで得られる（何をどのように調べればいいかわからない人にとっては有益です）
・必ずしもチームメイトは高め合える存在とは限らない（早々に進捗に差がでても最後まで同じチームメイトです。苦楽を共にする点では◯。ほぼずっとオンラインなので同じ進捗具合の別チームの方と交流する機会を設けてほしかった）

こんなところでしょうか。

上記と重複しますが、受講を検討されている方は、まずはProgateでプログラミングを遊んでみて、その後Udemyなどの動画教材で自学してみましょう。
わからないところはMenta等を利用してみましょう。
限定的ではありますが、福岡市内在住の方でしたらTechCampから徒歩5分程度のところに市が運営するエンジニアカフェというコワーキングスペースが無料で利用でき、午後からは駐在のエンジニアに質問することもできます。
上記のようなことをやってみて、どうしてダメだという方は検討してみてもいいかと思います。

以上になりますが、満足度は半々と行った感じです。
受講料がもう10〜15万でも安ければ満足が高かったと思います。

ただ後悔はしてません。
自分で選んで、そしてやりきった自負があるからです。

最後になりますが、TechCampでお世話になった方々、心から感謝しております。
そしてこの記事が誰かの参考に少しでもなれば幸いです。
Railsのエラー画面を見やすくするgem

#エラー画面を見やすくするgemを導入する


```Gemfile
group :development, :test do
  gem 'better_errors'
  gem 'binding_of_caller'
end
```
`$ bundle install`

###導入前
![スクリーンショット 2020-09-15 18.24.16.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/420303/82fadf00-2bd5-3929-0b8f-1a624bf53c72.png)

###導入後

![スクリーンショット 2020-09-15 18.28.47.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/420303/f7f57d80-12af-9b8a-aa4a-06884921e868.png)

**Application Frames**
ここでは、自分の書いたコードを対象にエラーに関係する箇所を明示してくれています

**All Frames**
自分が書いた箇所以外(gemやActiveSupportなど)まで踏み込んでエラーに関係する箇所が表示されます


##ローカルホスト以外のIPを許可
このままではlocalhostからのアクセスにしか対応していない。
他の開発環境でも実行できるようにするには、許可するIPの設定をしなければならない。

```config/emvironments/development.rb

Rails.application.configure do
.
.
.
end

 # endの外に以下を追記
BetterErrors::Middleware.allow_ip! "0.0.0.0/0"
```
------
[参考](https://qiita.com/ryokky59/items/284892be879996e4f77c)
コマンドプロンプト小技集

##フォルダ内のファイルを一括して削除##
下記のようなフォルダ構成を想定。
各フォルダからtxtファイルを削除したい。
**<フォルダ構成>**
test
  |--AAAA\aaaa.txt
  |       bbbb.doc
  |       cccc.txt
  |--BBBB\dddd.txt
  |       eeee.xls
  |       ffff.txt      

###コマンド###

```
del /s *.txt
```
/s：サブフォルダも含めて削除するオプション


##ファイル名の一覧を取得##
###コマンド###
```
dir /b > list.txt
```

##再帰的な検索##
```
dir /b /s /a-d AAAA.txt
```

/b　　ファイル名のみ表示
/s　　サブディレクトリも再帰的に検索
/a-d　ディレクトリを除く
digdagプラグイン使用時の「java.net.UnknownHostException: central.maven.org」対応

digdagでプラグインを使用していて以下のようなエラーが発生した時の対応方法です。0.9.41より前のバージョンを使用していると発生します。

```
java.lang.RuntimeException: org.eclipse.aether.resolution.DependencyResolutionException: Failed to collect dependencies at ...
...
Caused by: java.net.UnknownHostException: central.maven.org
```

0.9.41で対応済みなので、それ以上のバージョンに上げれば即解決です。

※参考

- [リリースノート](https://docs.digdag.io/releases/release-0.9.41.html)
- [PR](https://github.com/treasure-data/digdag/pull/1321)


バージョンを上げることが出来ない状況なら、repositoriesに`https://repo1.maven.org/maven2/`を追加することでエラーを回避出来ます。


```yaml:例
plugin:
  repositories:
    - https://repo1.maven.org/maven2/
  dependencies:
    - .....
```
【GAS】HTMLメールで画像をインライン表示させる２つの方法

##概要
GASを使えば、アドレス一覧に一斉にメール送信したりできる（一斉送信の記事ではないです）。用途とすればやっぱりメルマガとか？だったらやっぱり、ただのテキストメールじゃなくてHTMLでカッコよく装飾したメールを送りたい！

で、HTMLの書き方なんて分からないから、よくある視覚的にHTMLメールを作れるサービスを使ってテンプレートを作った訳だけど、HTML部分をコピペしても画像が表示されない・・・。

この記事では、HTMLメールで画像をインライン表示させるときの.gs側の記述と.html側の画像部分の記述について、２つの方法を紹介。

##前置き...
・使用する画像はGoogleドライブ内にある。
・HTMLファイルの名前は「本文.html」。もちろん任意^^;

##①画像を添付してインライン表示させる
画像をメールに添付して、本文中にインライン表示させる方法。「コード.gs」がコチラ。

```javascript
function sendHtmlMailBlob(){ 
   
  //ドライブ内にある画像をgetBlob
  var imgA = DriveApp.getFileById('ドライブ内の画像のID').getBlob(); 
  var imgB = DriveApp.getFileById('ドライブ内の画像のID').getBlob(); 
   
  //本文.htmlをgetContent
  var html = HtmlService.createHtmlOutputFromFile("本文").getContent(); 

  //宛先と件名
  var mail = 'inlinemail@gmail.coi'; 
  var title = 'インラインメール'; 
   
  //メール送信
  MailApp.sendEmail({ 
    to: mail, 
    subject: title,  
    htmlBody: html, 
    inlineImages:{imgA:imgA, 
                  imgB:imgB} 
  }); 
}
```
HTML側、画像部分の記述がコチラ。

```html
<img src="cid=imgA">
```

作成サービスで作ってダウンロードしたコード内に`src=画像の名前`みたいに画像を指定してる部分があるので、`src="cid=画像の名前"`に書き直してあげればOK！

##②画像のリンクからインライン表示させる
画像そのものは添付せず、画像のURLからインライン表示させる方法。「コード.gs」がコチラ。

```javascript
function sendHtmlMailURL(){
  
  //本文.htmlをgetContent
  var html = HtmlService.createHtmlOutputFromFile("本文").getContent(); 

  //宛先と件名
  var mail = 'inlinemail@gmail.coi'; 
  var title = 'インラインメール';
  
  //メール送信
  MailApp.sendEmail({
    to: mail,
    subject: title, 
    htmlBody: html,
  });
}
```
HTML側、画像部分の記述がコチラ。

```html
<img id="source" src="https://drive.google.com/uc?export=view&id=画像のID">
```
ここでポイントが２つ
・`src="共有可能なリンク"`ではない。
・画像の共有設定は「リンクを知っている全員」。

##補足
【画像のID】
ドライブ内の画像の「共有可能なリンク」の、次の部分がIDになる。
`https://drive.google.com/file/d/＜この部分＞/view?usp=sharing`

【画像の属性】
HTML部分の記述で画像の属性を省略してるけど、もちろん定義してOK。

###おしまい
テスト駆動開発(TDD)を身に着けるために、知るべきこと


業務でテスト駆動開発(TDD)を実践するようになってから約 2 か月が経ち、現在のチームでの開発スタイルにも慣れてきました。
TDD の実践のため、ケント・ベック氏の「テスト駆動開発」を読んだところ、TDD 初心者が知るべき内容が多いと感じたので、私のような方に共有できればと思います。

## テストの粒度

TDD を行っていると、テスト実装の際このような疑問が浮かんでくる。

> ・各々のテストがどのくらいをカバーすべきか  
> ・リファクタリングの家庭で中継地点をどのくらい作るか

ロジックに一行加えることや、少量のリファクタリングを行う際にテストを書くべきか？
ロジックに数百行加えたり、数時間かかるリファクタリングを行う際にテストを書くべきか？

この答えは、**「どちらもできるようになろう」**だ。
小さいステップで行うのがテスト駆動開発者の傾向ではあるが、アプリケーションレベルのテストのみで駆動する人もいるようだ。

リファクタリングを行う際には、ステップはたくさんの小さいステップに分割することを心掛ける。小さいステップのリファクタリングを複数回繰り返すことで間違いの入りにくいリファクタリングを行える。

## テストしなくてよいものはあるか

この質問には、以下がシンプルな答えと述べている。

> 不安が退屈に変わるまでテストを書く

具体的には、以下がテストすべき対象である。

> ・条件分岐
> ・ループ
> ・操作
> ・ポリモーフィズム

ただし、**自分の書いたコードに限る**(信頼できないと考える理由がある場合は除く)。
外部由来のバグによって、より多くのロジックを自分で書かなければならない場合、上記のリストをテスト項目として使う。

さらに慎重を期する場合、バグを記録するテスト(学習用テスト)を書いておく。
もしバグが修正された場合、そのテストが失敗して教えてくれる。

## 良いテストを見分けることができるか

アプリケーションの設計に問題を抱えている場合、テストには以下のような兆候が現れる。

・**前準備に要するコードが長い**
アサーションを行うテスト対象オブジェクトの準備に 100 行も必要なのであれば、オブジェクトが大きすぎるので、分割すべきだ。

・**前準備コードの重複**
共通の前準備コードを配置する場所がすぐに見つからない場合、互いに密に関連しあうオブジェクトが多すぎる事を示唆している。

・**テスト実行時間が長い**
TDD において、時間がかかるテストは実行の頻度が低くなる。そして長い間動かしていないテストは、おそらく通らなくなっている。長い実行時間は、アプリケーションの一部を切り出したテストが難しいことを示唆している。

・**脆いテスト**
思わぬタイミングで失敗するテストは、アプリケーションのどこかが意外な形で他の部分に影響している可能性を示唆している。離れた箇所からの影響を排除するように設計し直さなければならないかもしれない。

## どのような時にテストを消すべきか

もし 2 つのテストの間に重複が発生した場合、2 つとも残しておくべきか？
2 つの基準で判断すべきだ。

・**自信があるか？**
テストを消すことでシステムの振る舞いに対する自信が減るのであれば、決して削除してはならない。

・**同じシナリオと解釈できるか？**
2 つのテストがコードの同じ部分を実行しているとしても、読み手から異なるシナリオと映るのであれば、消さないでおく。

## 巨大なシステムをテストできるか？

重複の除去された小さなオブジェクトで構成されるアプリケーションでは、機能の総量は TDD の有効性とは無関係である。
その理由は、システムの大きさに関係なく個々のオブジェクトが独立してテスト可能だからである。

## アプリケーションレベルのテストで開発を駆動できるか？

小さなレベルのテストで開発を駆動する際に問題になるのは、顧客が望んでいる物を作れるかどうか？という点である。このリスクを排除するために、アプリケーションレベルのテストを導入すべきだ。  
もちろん、アプリケーションレベルのテストを走らせるための技術的な問題、そしてチーム全体でテストを書くことを浸透させるという文化的な問題がある。

## TDD は誰のためのものか？

TDD は、動くかわからないコードをコピペしてつなぎ合わせ、そのコードから目を背け平気な顔をしているような開発者のためのものではない。TDD は以下のような仮説で成り立っている。

> 「より良いコードを書けば、よりうまくいく」

これの意味するところは、正しいタイミングで正しい問いに気づける、より綺麗な設計になる、学びを得るにしたがってさらに設計を改善できる、といった事である。
プロジェクトを成功に導くという観点では、TDD はやりすぎとも言えるかもしれない。しかし欠陥数は大幅に減り、設計は明確になる。

エンジニアからしても、プロジェクトのコードを腐らせることなく、コード、システムに対する自信を持て、より多くの変更が可能になる。

## なぜ TDD は機能するのか？

TDD が必ず欠陥を減少させるという根拠はないが、事例証拠は多数あり、副次的効果は明白だ。
TDD が設計判断のフィードバックループを短くするということも、優位性を示す証拠になりうる。

TDD は、正しいコードを「引き寄せる」ようなプログラミングプラクティスである。
全てのテストが通る状態で機能を一度に 1 つ追加する、という状況は、状態空間中の全ての軌道が収束する点(数学用語でいうアトラクター)を作り出していることに等しい。
AndroidエンジニアがFlutterはじめてみた

Androidエンジニアで、Java/Kotlinくらいしか触って来なかったのですが、この度Dart/Flutterに入門してみました。
[Flutter公式](https://flutter.dev/)
そのときに知ったことや理解したこと等を書き記しておこうかなと思います。

## 対象読者
- Androidのアプリはなんとなく作れる人

## SDK Download
https://flutter.dev/docs/get-started/install
まずSDKのDLをしておく。

## AndroidStudioで始める
AndroidStudioには、Flutterのプロジェクトを生成するためのものはだいたい入っているらしい。
AndroidStudioの``File > New > New Flutter Project``でFlutterのProjectは作れる。
また、FlutterPluginもあるので、PluginsからInstallする。
Emulatorや実機がつないであれば、普通のAndroidProjectのようにRunを走らせれば、Hello Worldな画面が出てくる！

## コードを見ていく
- ``pubspec.yaml``が``build.gradle``にあたるもの。libraryの追加はそこに記載し、``pub get``で取ってくる。
- ``main.dart``から始まる。``runUp()``でMaterialAppを呼び出し。
- ``MaterialApp``がAndroidのApplication相当か。全体の``Theme``の設定もここでできる。
- ``build(context)``で画面全体を作る。``MaterialApp``の``home``が最初のページ。
- ``home``には``Widget``が配置できる。``Widget``はUIすべてで、``Activity``でもあり``View``でもある。
- この段階で[codelabs](https://flutter.dev/docs/codelabs)を試せるので、codelabsをやっていくと理解が進みやすいと思う。

## Widgetについて
- Widgetは主に``StatefulWidget``か``StatelesWidget``のどちらかで作られる。
- [StatelessWidget](https://api.flutter.dev/flutter/widgets/StatelessWidget-class.html)
 - 動的に変更がおこらない、静的なビュー。TextやButton等、「一度値を与えたら変更されないView」になります。（ボタンタップ等でText等が変更される画面等ありますが、あれは「Text自体」じゃなくて「Textの親Widget」が``StatefulWidget``なので変更ができます）
- [StatefulWidget](https://api.flutter.dev/flutter/widgets/StatefulWidget-class.html)のReferenceはこちら
 - ``StatefulWidget``は可変Propertyを持ったStateクラスを定義し、そのPropertyを使ってWidgetを変更していくもの。動的に変更が起こるクラス。
 - ``StatefulWidget``のStateから親のStatefulWidgetは``widget``として参照可能。なのでconstructor等での引き渡しは不要。
 - ``StatefulWidget``のStateを更新した場合は対象のWidgetとその子Viewまで含めて更新されてしまうので、更新が一部のViewだけの場合は、``StatelessWidget``を親に、``StatefulWidget``を継承した``ValueListenableBuilder``等の一部View単位の``StatefulWidget``を活用すると良い。
  
## Widget
[Widget Catalog](https://flutter.dev/docs/development/ui/widgets)
まずこのカタログ時点で便利

### 頻出と思われるWidget
- Center
- Row/Column
 - みんな大好きLinearLayoutのようなもの
- Padding
 - Default以外のPaddingつけるときはさらに囲うのびびる
- SizeBox
 - 上下にのみスペースいれたいとかだとこれ
- FutureBuilder:StatefulWidget. Future(非同期処理)の情報をもとに、Viewを更新する。
- ChangeNotifierProvider: ValueNotifierをもとに、Viewを更新する。

## いろいろ所感
- ``Button``の``onPressed()``の引数をnullにするとdisableになる。おもしろい。
- Widgetは結構ネストされまくるので適宜メソッドわけないと見づらい。
-　``StatefulWidget``のおかげで、Event等でのViewの変更はわりと書きやすいなと感じる
-　Viewをコードで書いていくのはAndroidもJetPackComposeが出てきたので多分流行りなんだろうし、なれておくといいと思うう
- enumに値をもたせられないのはちょっと面倒。extensionが増殖する。
- 「このエラー何！？」ってなったらセミコロン抜けてたあるある
- いろんなViewについて検索すると、公式DOCのサンプルコードがブラウザ上で変更可能な状態であるので便利です。

気づいたことがあったらさらに追記して行こうと思います。
JSONとは

#JSONについて
JSON (JavaScript Object Notation)は、データ交換フォーマットの一種で、 名前にはJavaScriptと入っているが、現在ではJavaScriptに限らず、 各種プログラム言語で利用できる。 
特徴としては、テキスト形式で可読性が高いこと、単純で軽量なことなどが挙げられます。 JSONは、同様にテキストベースであるXML(Extensible Markup Language)と比べてもよりシンプルであり、 各種言語との親和性も高く使い勝手も良いことから、 最近はWebアプリケーションなどで利用されている。

JSONのフォーマットでは、四つの基本的な型(文字列、数値、ブール値、null値)と、 二つの構造型(オブジェクト、配列)を表現できます。 単純なため、JSONはJavaScriptだけではなく、 C、C++、Objective-C、Java、Perl、Ruby、Pythonなど、 現在は多数の言語で利用可能になっている。そのため、これらの言語をまたいで、 あるいはネットワークを通して、データを交換できる。


##JSONの文法
{ ... } の中に、変数名と値をコロン(:)で区切り、下記の様に記述する。

```
{ "name": "Yamada" }
```
カンマ(,)で連結することにより、複数の変数名と値のペアを指定することができる。

```
{ "name": "Yamada", "age": 28 }
```

変数名(name や age)はダブルクォーテーション(")で囲む。JavaScript ではシングルクォーテーション(')で囲んだり、変数名をそのまま記述することができますが、JSON ではダブルクォーテーションのみとなる。

```
○ { "name": "Yamada", "age": 28 }
× { 'name': "Yamada", 'age': 28 }
× { name: "Yamada", age: 28 }
```

読みやすさのために、インデントをつけて表記されることも多いようです。インデントは 4文字スペースや 2文字スペースがよく用いられる。

```
{
  "name": "Yamada",
  "age": 28
}
```

下記の様に、配列や値のみの表記も JSON に従ったデータとして認められる。

```
○ ["ABC", "DEF"]
○ "ABC"
○ 123
```

JSONのエンコーディング
過去の仕様では単に Unicode が推奨され、先頭の 2バイトで UTF-8, UTF-16LE, UTF-16BE, UTF-32LE, UTF-32BE を見分けるとされていたが、RFC 8259 で指定された仕様では、BOM 無しの UTF-8 で記述する(MUST)と定義されている。

JSONの型
JSON では下記の通りである

```
文字列 ("...")
数値 (123, 12.3, 1.23e4 など)
ヌル値 (null)
真偽値 (true, false)
オブジェクト ({ ... })
配列 ([...])
文字列("...")
```

ダブルクォーテーション(")で囲んだ文字列を指定します。

{ "name": "Yamada" }
文字としては、0x00～0x1F までの制御文字、ダブルクォーテーション(")、バックスラッシュ(\)を除く、UTF-8 でエンコードした Unicode 文字列を使用できます。サロゲートペアも使用可能です。ダブルクォーテーション(")、バックスラッシュ(\)を使用するには、下記のエスケープシーケンスを使用します。

```
\" ... ダブルクォーテーション(")
\\ ... バックスラッシュ(\)
\/ ... スラッシュ(/) ... 単にスラッシュ(/)のみを記述することも可能
\b ... バックスペース
\f ... フォームフィード
\n ... ラインフィード
\r ... キャリッジリターン
\t ... タブ
\uXXXX ... Unicode文字(UTF-8でエンコードした文字でも可能)
数値(123, 12.3, 1.23e4)
```

123, 12.3, 1.23e3 などの数値を指定します。

{
  "age": 26,
  "pi": 3.14,
  "planck_constant": 6.62607e-34
}
数値は IEEE 754 の 64ビット倍精度の数値として扱われます。整数の場合は -2^53+1(-9,007,199,254,740,991)～2^53-1(9,007,199,254,740,991) の精度を扱うことができます。浮動小数の場合は、仮数部53ビット(10進数で15～16桁)、指数部11ビット(10進数で-1022～+1023)の精度を扱うことができます。精度を超える場合は丸め誤差が発生します。

ヌル値(null)
値が無いことを示すヌル値を null で指定します。null はすべて小文字で指定します。

```
{
  "name": null
}
```

真偽値(true, false)
真偽を true または false で指定します。true や false はすべて小文字で指定します。

```
{
  "active_flag": true,
  "delete_flag": false
}
```

オブジェクト({...})
オブジェクトを {...} で指定します。オブジェクトは階層構造を持つことができます。

```
{
  "user_info": {
    "user_id": "A1234567",
    "user_name": "Yamada Taro"
  }
}
```

配列([...])
配列を [...] で指定します。配列要素には、文字列、数値、ヌル値、真偽値、オブジェクト、配列すべてを使用することができます。

```
{
  "color_list": [ "red", "green", "blue" ],
  "num_list": [ 123, 456, 789 ],
  "mix_list": [ "red", 456, null, true ],
  "array_list": [ [ 12, 23 ], [ 34, 45 ], [ 56, 67 ] ],
  "object_list": [
    { "name": "Tanaka", "age": 26 },
    { "name: "Suzuki", "age": 32 }
  ]
}
```
VB.netで乱数を生成

VB.netで乱数を生成して、テキストボックスに文字列化するコード


```vb
    Sub GenRandom()
        Dim si As String = ""
        Dim n As Integer
        For n = 0 To 6 - 1
            Dim i As Integer = r.Next(10)
            si &= i.ToString()
        Next
        TextBox1.Text = si


        Dim arrayLarge() As String = {"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"}
        Dim sl As String = ""
        For n = 0 To 5 - 1
            Dim c As Integer = r.Next(26)
            sl &= arrayLarge(c)
        Next
        TextBox2.Text = sl

        Dim arraySmall() As String = {"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"}
        Dim ss As String = ""
        For n = 0 To 5 - 1
            Dim c As Integer = r.Next(26)
            ss &= arraySmall(c)
        Next
        TextBox3.Text = ss
    End Sub
```
Ubuntu 18.04.5 LTSへのOpenMXのインストール

OpenMXという第一原理計算ソフトがあります。第一原理計算とは、固体の位置情報から電子状態を計算する枠組みです。密度汎関数理論に従い、多体の電子状態が原理的には求まります。ただし、実際の計算では近似を色々かけているので、人によっては第一原理計算とは呼ばない人もいるかもしれません（化学分野の人は特に）。ともかく、ここでは第一原理計算ソフトと呼ぶことにします。

http://www.openmx-square.org/openmx_man3.9jp/index.html

このソフトをUbuntu 18.04.5 LTSにインストールしようとしたら思いのほかはまりましたので、解決方法をシェアすべくここに書きたいと思います。
まず、日本語マニュアルのmakefileの例はgfortranの場合には間違っているので、気をつけてください。

[注]mpirunで2並列にしたら落ちましたので、もしかしたらまだ間違っているかもしれません。誰か知っている方ご協力していただけると助かります。

VirtualBoxを用意して、まっさらなUbuntu 18.04.5 LTSに対してOpenMXをインストールした時の作業記録をここに残します。
以下はターミナルで実行したコマンドです。

```
wget https://apt.repos.intel.com/intel-gpg-keys/GPG-PUB-KEY-INTEL-SW-PRODUCTS-2019.PUB
sudo apt-key add GPG-PUB-KEY-INTEL-SW-PRODUCTS-2019.PUB
sudo sh -c 'echo deb https://apt.repos.intel.com/mkl all main > /etc/apt/sources.list.d/intel-mkl.list'
sudo apt-get update
sudo apt-get install intel-mkl-2020.0-088
sudo apt install gfortran
sudo apt install emacs
sudo apt install openmpi-doc openmpi-bin libopenmpi-dev
echo "source /opt/intel/mkl/bin/mklvars.sh intel64" | cat >> ~/.bashrc
sudo apt install libfftw3-3 libfftw3-dev libfftw3-doc
wget http://t-ozaki.issp.u-tokyo.ac.jp/openmx3.9.tar.gz
wget http://www.openmx-square.org/bugfixed/20Feb11/patch3.9.2.tar.gz
tar -xvf openmx3.9.tar.gz 
cp ./patch3.9.2.tar.gz openmx3.9/source/
cd openmx3.9/source
tar zxvf patch3.9.2.tar.gz
mv kpoint.in ../work/

```

何をしたかと言いますと、

- MKLのインストール
- gfortranのインストール
- emacsのインストール
- openmpiのインストール
- FFTW3のインストール
- OpenMXのダウンロード
- OpenMXのパッチを当てる

です。
次に、Makefileをいじります。

```
emacs makefile &
```
makefileは

```
MKLROOT = /opt/intel/mkl
CC = mpicc -O3  -fopenmp 
FC = mpif90 -O3  -fopenmp
LIB = -lgfortran -lmpi_mpifh -L${MKLROOT}/lib/intel64 -Wl,--no-as-needed -lmkl_scalapack_lp64 -lmkl_gf_lp64 -lmkl_gnu_thread -lmkl_core -lmkl_blacs_intelmpi_lp64 -lgomp -lpthread -lm -ldl -lfftw3
```
しておけばOKです。
このままだとmakeがインストールされていないので、

```
sudo apt install make
```
をします。
そして、

```
make all
```
をします。
このmakeですが、Ubuntu特有なのか面白いことが起きます。
途中で、

```
 `sqrt' に対する定義されていない参照です
```
みたいなエラーを吐いて落ちます。
どこで落ちたかみてみると、

```
mpicc  -O3  -fopenmp  -I./elpa-2018.05.001 -g   gcube2oned.c   -o gcube2oned
```
でです。
sqrtが定義されていない、というエラーはmathのライブラリーがリンクされていない時に起こります。
ですので、-lmオプションをつければ良いのですが、Ubuntuの場合、なぜか最後尾に-lmをつけないと同じエラーが出ます。
したがって、


```
mpicc  -O3  -fopenmp  -I./elpa-2018.05.001 -g   gcube2oned.c   -o gcube2oned -lm
make all
```
としましょう。
これで、この部分だけちゃんと-lmでコンパイルし、その続きをmake allでできます。

最後に、

```
make install
```
します。


動作確認には、

```
cd ../work
mpirun -np 1 openmx Methane.dat -nt 1 > met.std
cat met.std 
```
をして、

```
The calculation was normally finished.
```
が出ていれば大丈夫でしょう。
再インストールしてもRoomがVersionが違うとクラッシュし続ける場合の対処法

RoomでSchemaを変更したにもかかわらずDatabaseのバージョンを変更していないと以下のログが出てクラッシュします。

> java.lang.IllegalStateException: Room cannot verify the data integrity. Looks like you've changed schema but forgot to update the version number. You can simply fix this by increasing the version number.

おっしゃるとおり、Versionを上げてMigrationを書くのが正攻法なのですが、開発中でまだ定義が定まっていない時に毎回Versionを上げてMigartionを書くのは馬鹿らしいですよね。開発中のデータなんて消えても問題ないのであれば、schemaを変更したときはversionを上げて `fallbackToDestructiveMigration` で消しちゃえばいいです。

```kotlin
        Room.databaseBuilder(
            context,
            RoomDatabase::class.java,
            "room_database"
        )
            // Version違ってMigrationなかったら消しちゃう
            .fallbackToDestructiveMigration()
            .build()
```

とはいっても、毎回versionを変えるのすらめんどくさい。そういうときもあるとおもいます。人間ですからね。そんなときはアプリを再インストールすればマイグレーションもなにも無いだろうと思うかもしれませんが、再インストールしてもMigrationコードが無いとクラッシュする場合があります。

これは、 `AndroidManifest.xml` で `android:allowBackup=true` が設定されているとDB情報がバックアップされてしまうからです。 `allowBackup` はデフォルトでtrueが設定されているため、明示的にfalseを設定してあげないといけません。アンインストールしてもVersionが違うとクラッシュし続ける場合は確認してみましょう。
[漏洞通告]CVE-2020-1472/Netlogon 特权提升漏洞

### 漏洞描述
近日亚信安全网络攻防实验室监测到境外有发布Microsoft  NetLogon特权提升漏洞（CVE-2020-1472）相关poc代码，该漏洞是微软在2020年8月11日发布的安全更新通告中，修复的一个CVSS 10分的Windows NetLogon特权提升漏洞。通过Netlogon 远程协议（MS-NRPC）建立与域控制器连接安全通道时存在漏洞，远程（本地网络）攻击者可以利用此漏洞无需身份验证获取域控制器的管理员权限，由于该漏洞威胁十分严重，亚信安全网络攻防实验室在第一时间对该漏洞进行跟踪分析。

### 漏洞编号
CVE-2020-1472

### 漏洞威胁等级
高危

### 影响范围
Windows Server 2008 R2 for x64-based Systems Service Pack 1
Windows Server 2008 R2 for x64-based Systems Service Pack 1 (Server Core installation)
Windows Server 2012
Windows Server 2012 (Server Core installation)
Windows Server 2012 R2
Windows Server 2012 R2 (Server Core installation)
Windows Server 2016
Windows Server 2016  (Server Core installation)
Windows Server 2019
Windows Server 2019  (Server Core installation)
Windows Server, version 1903 (Server Core installation)
Windows Server, version 1909 (Server Core installation)
Windows Server, version 2004 (Server Core installation)

### 漏洞验证
使用公开的payload进行验证
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/491410/0a4b5eb0-9f39-6c9a-e065-e17f84f3a033.png)

### 简单分析
通过Netlogon 远程协议 (MS-NRPC) 建立与域控制器连接安全通道时存在的特权提升漏洞，成功利用此漏洞无需身份验证即可获取域控制器的管理员权限。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/491410/7ef5875e-55b5-8f6d-23b7-b21049a929c3.png)

### 修复建议
安装相应补丁包，补丁包下载:
https://portal.msrc.microsoft.com/zh-CN/security-guidance/advisory/CVE-2020-1472

### 时间轴
[0] 2020/09/15 亚信安全网络攻防实验室分析&复现该漏洞并发布漏洞通告

### Reference
https://portal.msrc.microsoft.com/zh-CN/security-guidance/advisory/CVE-2020-1472
https://support.microsoft.com/zh-cn/help/4557222/how-to-manage-the-changes-in-netlogon-secure-channel-connections-assoc
https://www.secura.com/pathtoimg.php?id=2055
https://github.com/SecuraBV/CVE-2020-1472/
SCSS Compassメモ

scssは入れた。
なんか動いた。

sublime textであーだこーだして、自動変換できるようにした。
でも、保存場所の指定とか個別する方法がわからなかった。_(┐「ε:)\_
なのでCompassを入れようと思った。

```sh:エラー
$ sudo gem install compass
(略)

extconf failed, exit code 1

Gem files will remain installed in /Library/Ruby/Gems/2.6.0/gems/ffi-1.13.1 for inspection.
Results logged to /Library/Ruby/Gems/2.6.0/extensions/universal-darwin-19/2.6.0/ffi-1.13.1/gem_make.out
```
あばば
調べる。

xcodeがなんか足りぬ
xcodeは最新の11.7が入ってた。
GUIで入れようとしたけど、「Command Line Developer Tools」の11.7がない。
ので、先駆者の参考ページ見ながら、下のコマンドで。

```sh:エラー
$ sudo xcodebuild -license
xcode-select: error: tool 'xcodebuild' requires Xcode, but active developer directory '/Library/Developer/CommandLineTools' is a command line tools instance
```
あばばb
Googleセンセー！

xcodeでCommand Line Toolsを設定する場所を発見。
参考ページ様のリンクわからなくなりましたすみませんんありがとうございます。

```:xcode
[xcode] => [preferences]
 => [locations] -> Command Line Tools: [ココを設定!!!]
```

で、

```sh:さくせす
$ sudo xcodebuild -license
(同意しておk)
```

で、

```sh:あーーー
$ sudo gem install compass
ERROR:  While executing gem ... (Gem::FilePermissionError)
    You don't have write permissions for the /usr/bin directory.
```

権限のLvが足りないってことらしい。(　˙-˙　)
いざレベル上げ٩( ᐛ )و

```sh:.bashrc
[[ -d ~/.rbenv  ]] && \
  export PATH=${HOME}/.rbenv/bin:${PATH} && \
  eval "$(rbenv init -)"
```

```sh
$ source ~/.bashrc
$ sudo gem install compass
(略)
Done installing documentation for chunky_png, sass, compass-import-once, multi_json, compass-core, compass after 3 seconds
6 gems installed

$ compass -v
Compass 1.0.3 (Polaris)
Copyright (c) 2008-2020 Chris Eppstein
Released under the MIT License.
Compass is charityware.
Please make a tax deductable donation for a worthy cause: http://umdf.org/compass

```

わーい_:(´ཀ`」 ∠):




#参考
- xcodeでCommand Line Tools設定を教えてくれたページ様
- [【Mac】SassとCompassをインストール！エラー克服版！ ( https://ocws.jp/blog/mac_terminal_sass_compass/ )](https://ocws.jp/blog/mac_terminal_sass_compass/)
- [gem installでpermissionエラーになった時の対応方法 ( https://qiita.com/nishina555/items/63ebd4a508a09c481150 )](https://qiita.com/nishina555/items/63ebd4a508a09c481150)
- [.bash_profileと.bashrcのまとめ ( https://qiita.com/takutoki/items/021b804b9957fe65e093 )](https://qiita.com/takutoki/items/021b804b9957fe65e093)
[Python]サブクラスのメソッドに特定の処理を強制する方法

# サブクラスに特定の処理を強制したい

Pythonでとあるクラスを継承したサブクラスを設計するとき、継承先には必ずこんな処理をして欲しい...なんてことがあります。

例えば`__init__`が呼ばれた時に必ずsuper().__init__()を呼んで欲しい...などの場合です。

`__init__`に限らず「親クラスのメソッドをオーバーライドしたいけど、親クラスのメソッドもそのまま呼び出したい！」なんて処理はよくよく現れるものですが、親クラスのメソッドを呼び出す処理を書き忘れてしまってエラーを吐かせるのはいやですし、そもそも親クラスのメソッドを呼び出す仕様そのものが面倒くさかったりしますね。

今回は子クラスのメソッド`f`が呼ばれるとき、その処理の後で必ず親クラスのメソッド`f`が呼ばれるような実装を実現してみます。

# やり方
**「子クラスの関数f」を「子クラスの関数fと親クラスの関数fを実行する関数new_f」に書き換える**
ってことをやってくれるメタクラスをかく

メタクラスってなんや？って話はまた今度違うところでします。とりあえずはクラスの定義のされ方をいじるクラスだと思っておいてください。

よくわからない人でも下記コードをコピーペーストして`decorate`メソッドを書き換えるだけでなんでもできると信じています。

# 前提
Python: 3.7.2  (Python3なら多分OK、Python2でもmetaclassの指定方法が違うだけなはず)

# コード

```python
class ParentCaller(type):
    def __new__(cls, name, base, attr):
        # ParentクラスのfがParentクラスのfを呼ぶのを防ぐ
        if name != "Parent":
            # クラス生成時、関数fは自動的にデコレートされる仕様にする
            attr["f"] = cls.decorate(attr["f"])
        return super().__new__(cls, name, base, attr)

    @classmethod
    def decorate(cls, f):
        # 関数fを受け取ると、fとParent.fをセットで実行するnew_fを返す
        def new_f(self, x):
            f(self, x)
            Parent.f(self, x)
        return new_f


class Parent(metaclass=ParentCaller):
    def f(self, x):
        print(f"parent's f says: {x}")


class Child(Parent):
    def f(self, x):
        print(f"child's f says: {x}")


child = Child()
child.f("Hello World!")

#  child's f says: Hello World!
#  parent's f says: Hello World!
```

# まとめ
Tensorflowのように人に継承して使ってもらうライブラリを書くときにはなるべく「ここでhogehogeを実行してね！」っていうお約束を避けたいものです。そんな時はメタクラスを書いて相手の知らないところで勝手にhogehogeを呼び出してしまいましょう。

集団での開発ではメタプログラミングって読みにくくて嫌われちゃうらしいですけどね...。個人で開発する分には工数を最小にしてくれるエッセンスなのではないかと思っています。
super()についてハッキリさせる

## 概要
pythonのクラス継承を行うsuper()、スーパークラスについて出てくるたびに調べ直していたので、使用方法をハッキリさせようと思う

## 用途
### `super()`とは
親クラスを継承する用途で使用する
継承されるクラスを継承するクラスの引数にとる

```python
class Parent():
    def __init__(self, plus):
        self.min = 20
        self.plus = plus
    
    def plus(self):
        age = self.min + self.plus
        return age

#親クラスのParentを引数にとることで継承する
class Child(Parent):
    def __init__(self):
        self.plus = 8
```

この状態で`Child().plus()`をしても`class Parent`の`__init__`が上書きされてしまう(`self.min`が無くなる)ため、エラーとなってしまう

つまり、以下のようにイメージだ

```python
class Parent():
    def __init__(self, plus):
        self.min = 20
        self.plus = plus
    
    def plus(self):
        age = self.min + self.plus
        return age

class Child(Parent):
    def __init__(self):
        self.plus = 8

    def plus(self):
        age = self.min + self.plus
        return age
```

従って、下記のようにすると親クラスのの`__init__`を継承するワケだ

```python
class Parent():
    def __init__(self, plus):
        self.min = 20
        self.plus = plus
    
    def plus(self):
        age = self.min + self.plus
        return age

#ここでの引数plusは関数のplusではなく、親クラスの__init__の引数のplus
class Child(Parent):
    def __init__(self):
        super().__init__(plus)
        self.plus = 8
```

`self.min`の値は継承され、28という値を出力できる

### `super()`の後は`__init__`か？

`super()`の後は`__init__`でなくてはいけないワケではなく、親クラスのメソッドであれば良い

```python
class Parent():
    def message(self, text):
        print('your name is: {}'.format(text))

class Child(Parent):
    def message(self):
        print('your friend is: {}'.format(text))
        super().message(text)    
```

## 文法
### `super()`内の引数について
python2系と3系で異なる

* __python2系__
  `super(親クラス名, self).親クラスのメソッド`

* __python3系__
  `super().親クラスのメソッド`

上記が標準のようだ

### `__init__()`内の引数について
先ほどの例にコメントで記載した

```python
class Parent():
    def __init__(self, plus):
        self.min = 20
        self.plus = plus
    
    def plus(self):
        age = self.min + self.plus
        return age

class Child(Parent):
    # selfに加えて、super()のinit()内で使われている引数を記載、引数の追加も可能
    def __init__(self, plus):
        # init()内はselfは省略して良い、デフォルト変数も省略可*、親クラスのinitと引数の数を揃える
        super().__init__(plus)
        self.plus = 8
```

※今回はデフォルト変数は使用していない

つまり、子クラスに関して

* `def __init__(引数)`の引数は
  * selfを記載
  * super()のinit()内で使われている引数を記載
  * 引数の追加も可能

* `super().__init__(引数)`の引数は
  * selfは書かない
  * 親クラスのinitと引数の数を揃える(selfを含む、ここでは2）
  * デフォルト変数は省略可能である




以上
tkinterで画像が表示できない時の解決【python】


tkinterで画像を表示させようとしたら

"~.png"は認識できませんでした。

となったので備忘録


#環境
Python 3.7.9
Tvl/Tk 8.6
Pillow==7.2.0

tkinterのバージョン確認

```python
import tkinter
tkinter._test() 
```

#本題

##問題のコード

```python

import tkinter
root = tkinter.Tk()

#前部省略

canvas = tkinter.Canvas(root, width=800, height=600)
canvas.pack()

img = tkinter.PhotoImage(file="my_picture.png")
canvas.create_image(400, 300, image=img)


#後部省略
```



どうやらtkinterのPhotoImageはかなり限定的な拡張子しか触れない様子。

pillowを使って解決

##解決コード

```python

import tkinter
from PIL import ImageTk, Image

root = tkinter.Tk()

#前部省略

canvas = tkinter.Canvas(root, width=400, height=600, bg="skyblue")
canvas.pack()

image = Image.open("my_picture.png")
photo = ImageTk.PhotoImage(image, master=root)
canvas.create_image(200, 300, image=photo)


#後部省略
```

#以上
node-poolを指定してdeploymentを作成メモ

# 背景
deployment作成する時にどのnode-poolで稼働するかを指定したい。
yamlファイルで指定する方法。

# やり方
#### node-poolの一覧取得

```
kubectl get nodes
```


#### yamlで指定
`nodeSelector` の `cloud.google.com/gke-nodepool` の項目にnode-pool名を指定する。

```yaml

apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  labels:
    app: sample-01
  name: sample-01
  namespace: default
spec:
  progressDeadlineSeconds: 600
  replicas: 1
  revisionHistoryLimit: 10
  selector:
    matchLabels:
      app: sample-01
  strategy:
    rollingUpdate:
      maxSurge: 25%
      maxUnavailable: 25%
    type: RollingUpdate
  template:
    metadata:
      creationTimestamp: null
      labels:
        app: sample-01
    spec:
      containers:
      - image: gcr.io/xxx/batch_server:20.08.19
        imagePullPolicy: IfNotPresent
        name: sample-sha256-1
        resources: {}
        terminationMessagePath: /dev/termination-log
        terminationMessagePolicy: File
      dnsPolicy: ClusterFirst
      nodeSelector:
        cloud.google.com/gke-nodepool: batch-pool # <- これ
~略~
```

# 参照
[Node上へのPodのスケジューリング](https://kubernetes.io/ja/docs/concepts/configuration/assign-pod-node/)
ディクショナリ型２

#ディクショナリ型２

get()
引数にキーを指定し、キーが存在する場合は対応する値が返り、キーが存在しない場合はNoneが返ります。
hatamoto = {'kokugo': 65, 'suugaku': 82}
>print(hatamoto.get('kokugo'))

実行結果
>65

>print(hatamot.get(‘rika’))

実行結果
>None

setdefault()
第一引数に「キー」、「第二引数に値」を指定する。
第一引数に指定した「キー」が対象のディクショナリに存在していない場合は、新たな要素が追加される。
>hatamoto = {'kokugo': 65, 'suugaku': 82}

>hatamoto.setdefault('eigo', 70)
>print(hatamoto)
> {'kokugo': 65, 'suugaku': 82,'eigo':70}

setdefault()で値を省略すると値がNoneの要素が追加される。
>hatamoto = {'kokugo': 65, 'suugaku': 82}

>hatamoto.setdefault('eigo')
>print(hatamoto)
> {'kokugo': 65, 'suugaku': 82, 'eigo': None}

キーがすでに存在している場合は、値を指定しても元のオブジェクトのまま変更されず、エラーは発生しない

>hatamoto = {'kokugo': 65, 'suugaku': 82}

>hatamoto.setdefault(kokugo': 62)
>print(hatamoto)
>hatamoto = {'kokugo': 65, 'suugaku': 82}



items()
items()メソッドはdict_itemsクラスを返します。

>hatamoto = {'kokugo': 65, 'suugaku': 82}
>items = hatamot.items()
>print(items)

>dict_items([(kokugo': 65), (suugaku': 82)])
Pythonでゼロから始める業務効率化

ボウリングのレーン配当表作成が、面倒くさい。よし、__PCにやらせよう__。

情報系に疎いプログラミング未経験者がツール実装に初挑戦してみました。初心者でもできる業務効率化の一例として、参考になればと思います。

#はじめに
競技ボウリングの大会では、プレイヤーをレーンに配当するための表が必要となります。
この配当表には、「一人のプレイヤーが2度以上同じボックスに配当されない」ことと、「任意の2人が、同じタイミングで同一ボックスに2度以上配当されない(要するに『またお前と同じボックスかよ』が発生しない)」ことが要求されます。ボウリング界隈以外の人はよく分からないと思うので、読み飛ばしてもらって構いません。
とにかく、これを手作業で作成+眼力でチェックするのは結構しんどい(人間がやると1時間以上かかる)ので、ツールを用いて自動化してみましょう。
ページの最後に完成品を置いたので、良ければどうぞ(需要、あるのか？)。

※2020/11/10 追記
不具合が判明したので一時的に公開を取りやめています。解消次第、再公開します。申し訳ありません。


#0.配当表完成までの大まかな流れ
①プレイヤーに乱数でレーンを割り振る
②条件を満たさない箇所を見つけ出す
③問題箇所に限ってシャッフルをかける
④問題箇所が0になるまで②③を繰り返す
⑤必要な情報を出力する

#1. Excelでやってみよう！
ひとまずExcelで乱数を使って手作業でレーン配当表を作り、問題箇所の検出のみを自動化しました。Excelの関数さえよく分からない状況からの出発なので、いろいろとググりながらチェック機構を実装しました。Excel関連の情報はネットに山ほど転がっているのでありがたい。
__問題点__
・各大会ごとにプレイヤー数や使用ボックス数が異なるので、チェック機構を毎回手作業で組む必要がある(面倒くさい)。
・Excelと組み合わせ列挙の相性がめちゃめちゃ悪い。

#2. Python編
面倒なので、さらに自動化を進めたくなってきました。よし、プログラミングでやってみよう。でもプログラミング言語何も使えないじゃん。ということで__Python3__を学びます[^1]。Pythonは視覚的にもめちゃくちゃわかりやすいので、初めての言語としてオススメです。ExcelVBA(いわゆる「マクロ」)も検討しましたが、扱いにくい&汎用性が低そうなのでやめました。
実装はひたすらやるだけなのですが、結構大変でした(AtCoderで言ったら、Diff800程度くらいの実装をひたすら繋げていく感じ)。最終的には400行くらいになりました。コーナーケース潰しの大変さも実感しました。
__問題点__
・Python上で文字列として入出力するので、Excelファイルとの間でコピペする必要があり、少々使いにくい

#3. openpyxl編
ここからは、入出力方式の改善を目指しました。
今回は、Python上でExcelファイルを扱えるopenpyxlモジュールを使いました。モジュールとは、道具箱みたいなもので、これをインポートすることによりPython上で出来ることが拡張されます。Pythonは特にモジュールが充実しているので、めちゃめちゃありがたい。このモジュールを用いることで、入出力をExcel上で行えるようになりました。openpyxlは特に有用なので、今後も積極的に使っていきたい。
__問題点__
・Pythonをインストールしていない人にはこのツールが共有できない

#4. tkinter編
さらに発展させて、枠に文字を入力することで動作し、レーン配当表をExcelファイルとして出力してくれるようなGUIアプリケーションにすることを目指しました。実際には、Pythonのtkinterモジュール(tinderじゃないよ)を使いました。前提知識0なのでひたすらググり続ける感じでしたが、学びも多かった。
書き上げたPythonのソースコードをpyinstallerを用いてexeファイル化することにより、GUIアプリケーションとして完成しました。これでPythonを使えない人でもツールを使えるようになりました。
![ScreenShot.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/713550/b7635615-1b3f-c279-a037-ffaa1d7c6030.png)
↑こんな感じで入力すると…
![ScreenShot_Product.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/713550/b3cf33a2-8cca-8dcd-0356-28c67e12620a.png)
↑こんな感じでExcelファイルとして出力される。

名前リストは2019年のPBA賞金ランキングから取ってきました。夢のような大会ですね。
#完成品
完成したアプリケーションは~~こちら~~(Dropbox)よりダウンロード可能です。
ぜひ遊んでみてください。
※Windows用とMac用で分かれているので、正しい方のフォルダをダウンロードしてください。

※2020/11/10 追記
不具合が見つかった為、一時的に公開を取りやめています。

# 最後に
最後まで読んでいただきありがとうございました。実はこのツールをWEBアプリケーション化することも考えたのですが、htmlの知識もゼロなのでひとまず断念しました。htmlに挑戦したらまた報告します。



#番外編
このツールの実装と並行して、プログラミングコンテストのAtcoderも始めました。競技プログラミングは役に立たん！みたいな話も聞きますが、リスト等の基本的な扱いに慣れるのには有用で、少なくとも緑色前半くらいまでの内容は非情報系の人々の実生活にも役立つような気がします。

[^1]: やさしいPython(高橋麻奈,SBクリエイティブ社), この本は名前に反して分かりやすかった、オススメです。