OmniAICreator/Qiita-1.07M huggingface dataset:
【TypeScript】TypeScript で シングルトンパターンを実装

#シングルトンとは
* シングルトンは、常に唯一のインスタンスであることを強制するデザインパターンです

##シングルトンの実装方法
* ①コンストラクタをprivateにすることで、クラス内のみで、コンストラクタにアクセスできるようにします
* ②private staticなフィールドに唯一のインスタンスを保存し、このクラスの中からのみアクセス可能にします
* ③static メソッドで、staticなフィールドにアクセスし、外部から唯一のインスタンスを取得できるようにします

```ts
class AccountingDepartment extends Department {

  private lastReport: string;
  private static instance: AccountingDepartment; //クラスの中からのみアクセス可能

  private constructor(id: string, private reports: string[]) {
    super(id, 'Accounting');
    this.lastReport = reports[0];
  }

  static getInstance() { //staticなプロパティにアクセスできる                      
    //AccountingDepartmentのインスタンスが存在していたら
    if (AccountingDepartment.instance) { 
      return this.instance; //staticメソッドでのthisはクラス
    }

    //インスタンスが存在しない場合、newして、this.instanceに格納
    this.instance = new AccountingDepartment('d2', []);  
    return this.instance;
  }

  describe() {
    console.log('会計部門 - ID: ' + this.id);
  }

}
```

```ts
//親クラス
abstract class Department {
  static fiscalYear = 2021;
  protected employees: string[] = [];

  static createEmployee(name: string) {
    return { name: name };
  }

  constructor(protected readonly id: string, public name: string) {
    console.log(Department.fiscalYear);
  }

  abstract describe(this: Department): void;

}

```

##シングルトンなインスタンスの取得方法

```ts
// const accounting = new AccountingDepartment('d2', []); //クラス外部でnewをさせない

//シングルトンなインスタンス取得
const accounting = AccountingDepartment.getInstance();
const accounting2 = AccountingDepartment.getInstance();

console.log(accounting, accounting2); //同じインスタンスを取得できている
```
gitで別のアカウントにpush/pullしたい場合

普段使わないリポジトリへのアクセスが必要になった際、複数githubアカウントの管理が必要になりそうだったのでメモ。

仕事用と個人用など頻繁に切り替える必要がある方は下記の記事を参考することを推奨します。
[複数のgitアカウントを使用する場合](https://qiita.com/yamataku29/items/4744c9c70ad793c83b82)

今回は、「１つのリポジトリのみ適用したい」という方向けな気がします。
## 変更すべき場所の確認
```sh:コマンド
$ cd .git/config
$ cat config

[core]
・・・
[remote "origin"]
        url = https://github.com/[ユーザー名]/[リポジトリ名].git # 変更箇所
        fetch = +refs/heads/*:refs/remotes/origin/*
[branch "main"]
・・・
```

## remoteのurlを変更
```sh:コマンド
$ git remote set-url origin https://[ユーザー名]:[パスワード]@github.com/[ユーザー名]/[リポジトリ名].git
```

## localを設定
これを設定しておかないと、コミット履歴にglobalで設定してあるアカウントが適用される。
```sh:
$ git config --local user.name "[ユーザー名]"
$ git config --local user.email "[メールアドレス]"
```
amplifyの作法 その8

#概要

amplifyの作法、調べてみた。
pyqubo使ってみた。

#サンプルコード

```
import numpy as np
from pyqubo import Array, LogEncInteger
from pyqubo import Constraint
from pyqubo import solve_qubo
from amplify import (BinaryPoly, BinaryQuadraticModel, gen_symbols, Solver, decode_solution, )
from amplify.client import FixstarsClient


m = 3
L = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
N = len(L)
M = 3
x = Array.create('x', shape = (N, m), vartype = 'BINARY')
y = LogEncInteger('y', (0, M))
A2 = 36
A1 = (A2 / max(L) ** 2) / 0.12
B = (A2 / max(L)) / 3.6
const = 0
for a in range(1, m):
    const += (M - sum([L[i] * (x[i, 0] - x[i, a]) for i in range(N)]) - y) ** 2
HA1 = Constraint(const, label = 'HA1')
HA2 = Constraint(sum((1 - sum(x[i, a] for a in range(m))) ** 2 for i in range(N)), label = 'HA2')
HB = sum(L[i] * x[i, 0] for i in range(N))
Q = A1 * HA1 + A2 * HA2 + B * HB
model = Q.compile()
sp = []
for i in range(10):
  for j in range(10):
    sp.append("x[" + str(j) + "][" + str(i) + "]")
sp.append("y[0]")
sp.append("y[1]")
sp.append("y[2]")
#print(sp)
qubo, offset = model.to_qubo()
#print(qubo.keys())
#print(qubo)
Q = {}
for i in range(103):
  for j in range(103):
    if ((sp[i], sp[j]) in qubo):
      Q[(i, j)] = qubo[(sp[i], sp[j])]
f = BinaryPoly(Q)
model0 = BinaryQuadraticModel(f)
solver = Solver(client)
result = solver.solve(model0)
solution = result[0].values
#print(solution)
print("仕事の数 : " + str(N) + "個")
print("コンピュータの数 : " + str(m))
print("仕事の長さのリスト : ")
print(L)

job_length = [0] * m
for i in range(0, m):
    print("コンピュータ" + str(i + 1) + "で行われる仕事")
    for j in range(0, N):
        if solution[i * N + j] == 1:
            print(str(j + 1) + "番目の仕事 長さ: " + str(L[j]))
            job_length[i] += L[j]
    print("仕事の総実行時間: " + str(job_length[i]))
    print()



```

以上。
CircleCI

#memo
- ビルド・テスト・デプロイを行うCICDツール
- SaaS型（コンテナ形式だからオンプレでも使える？）
- JenkinsのようにGUIでというよりはYaml
- Github連携が前提でSVNではつかえない




#参考
https://qiita.com/tatane616/items/8624e61473a9957d9a81

https://qiita.com/tatane616/items/8624e61473a9957d9a81
Railsでお気に入り機能を実装する

##自己紹介
9月から独学でプログラミング学習を開始し、
11月からスクールを使って学習をしています。
現在はポートフォリオの作成し転職活動中です。
知識を定着させるために、学びをアウトプットしています。
また、これから学び始める方の参考になることを願っています。
***
##開発環境
- Ruby 3.0
- Ruby on Rails 6.0.3.4

#お気に入り機能を実装する

今回は**socialization**というgemを使用します。
>▼詳しくは公式のGithubはご覧ください。
https://github.com/cmer/socialization

現在、**User**テーブルと映画情報を保存する**Movie**テーブルがあるとします。 
まずは、`Gemfile`に下記を追加します。

```
gem 'socialization'
```

追加したら、`bundle install`を実行し、gemを追加してください。

次に、`rails generate socialization -s`を実行します。
実行すると、`like.rb` `follow.rb` `mention.rb`のように
モデルが3つとマイグレーションファイルが3つ作成されます。

```rb
- class CreateFollows < ActiveRecord::Migration
+ class CreateFollows < ActiveRecord::Migration[6.0]
```
上記のようにそれぞれのマイグレーションファイルにバージョンを追加します。
そして`rails db:migrate`を実行してください。
###１．モデルを編集する
それぞれのモデルに下記を追加します。

```rb

class Movie < ApplicationRecord

  act_as_likeable

end
```

```rb

class User < ApplicationRecord

  act_as_liker

end
```

他にお気に入り機能を追加したいテーブルがある場合は、
同様に、`act_as_likeable`を追加して下さい。

---
###２．コントローラーを編集する
`/controllers/movies_controller.rb`を編集します。

```rb
class MoviesController < ApplicationController

def favorite
  @movie = Movie.find(params[:id])
  current_user.toggle_like!(@movie)
end
```

上記のように`favorite`を追加しています。

`current_user`を使用するには**devise**というgemが必要になります。
今回、deviseについては、省略致します。

**socialization**を導入したことで`user.toggle_like!(movie)`というメソッドが使えるようになりました。
これは、

- お気に入りされていなければ、お気に入り登録をする
- お気に入りされていれば、お気に入りを解除する

このようなメソッドです。
その他のメソッドについては、[公式Github](https://github.com/cmer/socialization)を参照下さい。

###3.ルーティングを編集する
`favorite`を追加したので`/config/routes.rb`を編集しましょう。

```rb
Rails.application.routes.draw do

  resources :movies do
    member do
      post 'favorite'
    end
  end

end
```
>メンバールーティングについてはRailsガイドを参照下さい。
https://railsguides.jp/routing.html

###4.ビューを編集する
```erb
<%= link_to favorite_movie_path do %>
  <% if current_user.likes?(movie) %>
    お気に入り解除
  <% else %>
    お気に入り登録
  <% end %>
<% end %>
```

先程、指定したルーティングを`link_to`で使用しています。
`current_user.likes?(movie)`
これは、ユーザーがお気に入り登録していると**true**を返します。

---
シンプルですが、基本的な機能の実装は以上です。
しかし、Ajax(非同期処理)でお気に入り登録をしたり、
お気に入りの総数を表示したいと思うかもしれません。
この辺りの実装は[Ajaxでお気に入り機能を実装する](https://qiita.com/KON-ch/items/a1186831b3cbd7f8e6a4)をご覧下さい。
何か、至らない点があれば、ご指摘下さい。
[TypeScript]文字列リテラルをテンプレートリテラルで分解し、型再帰で階層内の型を抽出する

# 必要なバージョン

今回の内容を実行するにはTypeScriptの4.1.2以降が必要です
型の変換等に関する定石は[こちら](https://ttis.croud.jp/?uuid=fb922d6a-f1d1-4899-b963-e7e2a4519e39)を見てください

# 実現する内容

```ts
const value = { aaa: { bbb: { ccc: 'Test', ddd: 100 } } }

const ccc = getTreeValue(value, 'aaa/bbb/ccc') //型は自動的にstring
console.log(ccc) //Test
const ddd = getTreeValue(value, 'aaa/bbb/ddd') //型は自動的にnumber
console.log(ddd) //100
```

オブジェクトからスラッシュ区切りでデータを取り出し型推論させます。
この処理を行う方法は以降の内容を確認してください。


# 文字列リテラルを分解し、再帰的に型を取り出す処理

```ts
type PickTree<T, P> = P extends keyof T
  ? T[P]
  : P extends `${infer R1}/${infer R2}`
  ? R1 extends keyof T
    ? PickTree<T[R1], R2>
    : never
  : never
```

文字列リテラルをテンプレートリテラルを経由し、inferで取り出して分解しています。後続の文字列は再帰で順次処理します。

# オブジェクトの階層を辿ってデータを取り出す

```ts
const getTreeValue = <T extends { [_ in any]: any }, K extends string>(v: T, path: K) =>
  path.split('/').reduce((a, b) => a[b], v) as TreePick<T, K>
```

こちらは実処理になります。文字列を分解して順番に内容を展開します。そして先ほど作ったTreePickで戻り値の型を決めます。


# まとめ

TypeScriptはバージョンが進むにつれて、今まで出来なかった事が実現可能になっていきます。
夢が広がります。
Java小テスト③ ~ while 編 〜

これは友達向けのJavaの小テストです。
Java初心者の文法腕試しでお使いくださいー！！

今日はwhile文の小テストを作りたいと思います！

問題①：次のプログラムを10未満の偶数の数を出力するように訂正せよ。

```java
while(i < 10) {
    System.out.println(i);
}

```
問題②：次の出力は何か？

```java
public class WhileClass {
    public static void main(String[] args) {
       int i = 0;
       while(i < 10) {
           if(i % 3 == 0 && i % 5 == 0) {
               System.out.println("FizzBuzz");
           } else if(i % 3 == 0) {
               System.out.println("Fizz");
           } else if(i % 5 == 0) {
               System.out.println("Buzz");
           } else {
               System.out.println(i);
           }
           i++;
       }
    }
}

```

問題③：次の問題に答えよ

> for文とwhile文はどのように使い分けるか？



問題④：以下を全て満たすプログラムをwhileを使って書け。

- ユーザーに2つの数字の入力を求める。
- 入力が数字でない場合は, 聞き直す。
- 2つの数字を入力後
    - 操作の数字を入力してもらう。
        - 入力が0であれば, プログラムは終了
        - 入力が1であれば, 2つの数を足した値を返す
        - 入力が2であれば, 2つの数を引いた絶対値を返す。
        - 入力が3であれば, 2つの数をかけた数を返す。
        - 入力が4であれば, 大きい方から小さい方を割った数を返す。(ただし, 小さい数が0だった場合はエラーを出力）
        - (入力が5以上であれば, 数字を聞き直す。) ← 出来れば。
Node-Redのinjectノードにおける繰り返し機能のタイムゾーンについて

# はじめに
Node-Redのinjectノードにおける繰り返し機能のタイムゾーンについてのメモです。
他の環境で再現するかどうかはわかりません。

# 環境
Node-REDの実行環境は[enebular](https://www.enebular.com/ja/)をつかっています。

# 直面した問題と解決方法
Node-Redのinjectノードにおける繰り返し機能を使おうと、日本標準時（JST）で指定したのですが設定した時間に動きませんでした。そこで、日時指定を協定世界時（UTC）で指定しところ、狙った時間にinjectノードが発火し動きました。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/212276/437757f3-1001-e7e1-e61a-bbd8a945ea97.png)

デバッグ画面で表示される時刻がJSTだったので、injectノードもJSTで指定するのだろう、と思っていましたが、なぜかUTCでした。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/212276/1ab521cd-cefc-6ce4-b4c0-7c0f6a1ad465.png)

# おわりに
動作させる環境で異なるかもしれません。
injectノードの繰り返し機能が上手く動かない、といった場合、UTCで設定すると上手くいくかもしれません。
【Node.js】npm proxyの使い方

#プログラミング勉強日記
2021年3月1日

#proxyとは
　proxyは、npm configコマンドで使用できる代理(プロキシ)サーバー設定のこと。
　開発中にインターネットでアクセスの制限をされた場合など、セキュリティの問題によってアクセス制限された環境でプロキシサーバーを経由した開発を行うことがある。

#使い方
　npmでプロキシサーバーの設定をするためには、npm configコマンドでproxyを使用する。npm config set proxyと入力することで、npm config機能の一部であるproxyを利用できる。

```
$ npm config set proxy http://<proxy-host>:<proxy-port>
```

```:proxyを解除する方法
$ npm -g config delete proxy
```

```:proxy設定の確認
$ npm -g config list
```

#参考文献
[プロキシサーバーを使う際に役立つ！npm proxyの使い方【初心者向け】](https://techacademy.jp/magazine/16379)
[Node.js / npm 設定 に プロキシ を 設定 または 解除 する 方法](https://garafu.blogspot.com/2017/11/nodejs-npm-proxy-config.html)
Qiita Daily Survey memo 2021.03.01

# Qiita Daily Survey memo 2021.03.01
Qiita の記事を可能な限り毎日読むために、読んだmemoを公開することでモチベーションを維持しようという試み。
3月になりました！
毎日 Qiita を見ているおかげか、興味のある分野や、良く紹介される分野について少し知識がついてきたかもです。
引き続き続けていきたいと思います。

## [【NoCode】5年目iOSエンジニアが、アプリのE2Eテスト自動化サービスを作った話](https://qiita.com/kot10n5tn/items/291ad1170cf00253bf3b)
岩佐 晃也(kot10n5tn) さんの記事。
iOSアプリのテスト自動化サービスを作りましたよ、という記事です。
iOSエンジニア歴5年目の方ということで、開発されていて「こんなのあったらいいな」を作成してくださったのかなと思います。
サービス開発にあたっての開発体制や大変だったところ、良かったところに加え、Appium Firebase の知見を書いてくださっています。

テスト自動化系大変ですものね…このようなサービスがあると非常に助かるのではと思います！


## [pythonでLINEのAPI簡単に使ってみた](https://qiita.com/Threen/items/3a5162b3002d2c77c63b)
Threen さんの記事。
Line の API を使って、hello world ( echo の確認 ) をしましたよ、という記事になります。
生活に近いということで、Line の API 使って xx というのがチャレンジしやすいですよね！
本記事でも echo ができたので、他の機能・作成物との組み合わせについて、何をしようかと考察されています。

[お風呂を沸かしてみたり](https://qiita.com/wimps/items/1140a62279800d876b81)、[推しのために人気投票のリマインダをつってみたり](https://qiita.com/Motchy_1204/items/788f5a61f2cdaada0da3) と、「こうだったらいいのにな」にチャレンジするのに強力なツールの一つだと思います。


## [Redmineのログ可視化ページがお蔵入りした話](https://qiita.com/Rahariku/items/1531955351fd411bc5b7)
Ruketa さんの記事。
プロジェクト管理ツール Redmine のログを可視化（レポーティング）したけど、使ってもらえなかっという記事になります。
記事を拝見させていただきましたが、作成されたもの及び概念図はとてもよくできていると感じました。
今私もタスク管理系のツールを作っているところなので参考にさせていただきたいと思いました。

また、以前仕事で事例調査を行ったことがあり、その際「失敗事例」を収集することになりました。
しかし、「うまくいったこと」は事例として多く紹介されていますが、「うまくいかなかったこと」が紹介されている場合は少なく、貴重な記事だと感じました。

私のタスク管理ツール（memo）では、各タスクの評価値（予定より早く着手できた、予定より早く終わらせることができた、連続〇日継続できている等々）でスコアリングし、一日の集計を取って今日は頑張れた/頑張れなかったをランク付けして評価したりしています。
「今日の評価がまだCランクか…じゃあもう少し頑張るか」とか、「今日はもうAランクになったのか…じゃあ後は整理だけして終わりにするか」とか、モチベーションと判断基準の一つになっています。

タスク管理系難しいですよね…。
私もツールを作っては使わなくなり、作っては使わなくなりで、なかなかうまく機能してないです…。
次こそは…！
ADX2の発音数制御まとめ

# 発音制御とは？
ゲームの画面内で起こっている出来事全てに対して音を鳴らしてしまうと、**大事な音が聞き苦しくなってしまう場合がある**ため、指定された条件に合わせて発音を間引く仕組みがADX2には用意されています。

このページではそれらの機能一覧と、それぞれのドキュメント、チュートリアルへのリンクをまとめていきます。


# 発音数を制限する機能と特徴について
優先度の高い順に

* ボイスリミットグループ
    * グルーピングしたボイスの同時発音数を制限します
* カテゴリキューリミット
    * 同一カテゴリ内でのキューの同時再生数を制限します
* キューリミット
    * 発音イベントである**キュー**の同時再生数を制限します
* キューシートキューリミット
    * キューシート単位でキューの同時再生数を制限します




## 理解しておくべき用語について
### キューとボイス
キューとは
https://game.criware.jp/manual/adx2_tool/latest/criatom_tools_atomcraft_cue.html

ボイスとは
https://game.criware.jp/manual/adx2_tool/latest/criatom_tools_atomcraft_voice.html

キューシートの分け方
https://game.criware.jp/manual/adx2_tool/latest/craftv2_tips_divide_cuesheet.html

ボイス数の制限
https://game.criware.jp/manual/adx2_tool/latest/craftv2_tips_decide_voicelimit.html


## 関連チュートリアル、Tipsリンク集
CRI ADX2(AtomCraft) 初級編10　キューリミット、プライオリティ、多重再生禁止時間
https://game.criware.jp/learn/tutorial/atomcraft/atomcraft_shokyu_10/

CRI ADX2(AtomCraft) 初級編11　ボイスリミットグループ
https://game.criware.jp/learn/tutorial/atomcraft/atomcraft_shokyu_11/


「発音数制限のグループとしてのカテゴリキューリミット」と「ボイスリミットグループのボイスリミット」の違い
https://game.criware.jp/manual/adx2_tool/latest/craftv2_tips_decide_use_category_limit_voice_limit.html

### 公式以外のTips

https://note.com/adx_kawaguchi/n/n2e28b57cafdd
A Tour of GoのExercise: Mapsを解く

# 考えたこと

https://go-tour-jp.appspot.com/moretypes/23

まず設問を理解します。

> string s で渡される文章の、各単語の出現回数のmapを返す必要があります。

ふむふむ、どうやら単語の出現回数を数えるのがこの問題の趣旨らしい。

> Note: このテストスイートで何を入力とし、何を期待しているかについては、golang.org/x/tour/wcを見てみてください。

とあるので、[golang.org/x/tour/wc](https://github.com/golang/tour/blob/master/wc/wc.go)をみてみると、テストケースがわかります。

```
	{"I am learning Go!", map[string]int{
		"I": 1, "am": 1, "learning": 1, "Go!": 1,
	}},
```

ここまでくると全容が見えてきます。
"I am learning Go!"のような形式で入力が与えられるので、スペースで区切って、I とか am とかが何回出現するか数える、
というのがこの設問の答えということがわかります。

さて、どうやってスペースで区切るかですが、

>strings.Fields で、何かヒントを得ることができるはずです。

と書いてあるので[strings.Fields](https://golang.org/pkg/strings/#Fields) をみてみましょう。

まさに求めていたスペースで区切る関数でした。
引数で与えられたstringをスペースで分割して、stringのスライスを返す関数のようです。

ここまできたら、材料は揃ったのであとは解くだけです。


# コード

```go:Maps
package main

import (
	"golang.org/x/tour/wc"
	"strings"
)

func WordCount(s string) map[string]int {
	m := make(map[string]int)
	// stringをスペースで分割する
	splited := strings.Fields(s)
	for _, val := range splited {
		// 出現回数を数える
		m[val]++
	}
	
	return m
}

func main() {
	wc.Test(WordCount)
}

```
【Angular】コマンド一つでGitHub Pagesにデプロイする方法


#GitHub Pagesにデプロイする

[fanzeyi/pokemon.json](https://github.com/fanzeyi/pokemon.json)から取得したポケモン一覧を表示するアプリケーションを先日作ったので、今回はこれをGitHub Pagesにデプロイしてみたいと思います。手順はたったの3つです。

ソースコード：https://stackblitz.com/github/oioigohan/pokemon-list
リポジトリ：https://github.com/oioigohan/pokemon-list
デプロイ結果：https://oioigohan.github.io/pokemon-list/

参考：[[Angular]デプロイしたサイトをGithub Pagesで表示する - CodeLab](https://codelab.website/angular-github-pages/)

## 1. angular-cli-ghpagesをインストールする

次のコマンドで`angular-cli-ghpages`をインストールします。

```shell
> npm install angular-cli-ghpages
```

## 2. アプリケーションをビルドする

インストールが完了したら、作ったアプリケーションを次のコマンドでビルドします。

```shell
> ng build --prod --base-href "https://[username].github.io/[repo]/"
```
`[username]`にはGithubのユーザ名、`[repo]`にはリポジトリ名に書き換えてください。リポジトリ名の末尾に.github.ioを含めておく必要はありません。

## 3. gh-pagesブランチにプッシュする

ビルドが完了したら、GitHub Pagesにデプロイします。次のコマンドで作業ブランチとは別に`gh-pages`というブランチが自動で作成されます。今後GitHub Pagesはそのブランチの内容を読み取ってくれます。

```shell
> npx ngh --dir=dist/[project-name]
```

`[project-name]`にはビルド後の`dist`ディレクトリ直下のディレクトリ名（プロジェクト名）に書き換えてください。

## デプロイができているか確認する

`gh-pages`ブランチにプッシュされたことが確認できたら、`https://[username].github.io/[repo]/`にアクセスしてみます。反映に数分かかることもあるので、404のページが表示される場合は少し待ちます。次のように正しく表示されていれば成功です。https://oioigohan.github.io/pokemon-list/

![pokemon-list deploy result](https://github.com/oioigohan/pokemon-list/raw/main/pokemon-list.png "デプロイ成功")

## 最後に

参考にさせていただいたサイトにも、

> Github Pagesを活用することでAngularのサイトでサーバサイドの実装が不要な場合に、環境構築など必要なく本番環境として利用することができます。クライアント側の処理だけでサイトが完成できるのであれば、サーバ代の節約にもなるので、積極的にGithub Pagesを活用していきたいですね。

とあるように、GitHub Pagesを使うメリットは大きいです。
実際使ってみて、フロントエンドの実装結果をすぐに確認できることに非常にありがたみを感じられました。手順が少なく簡単で、リポジトリも汚さないのでAngularの練習中の方、サイトをサクッと公開したい方におすすめです。
[PHP]定数のプロパティだとstaticプロパティになる


```php
class Foo {
     public $a = "aaa";
     public const b = "bbb";
 }
 
 $foo = new Foo();
 echo $foo->a;
 echo $foo->b;
```

## エラー

```
PHP Warning:  Undefined property: Foo::$b in /workspace/Main.php on line 10
```

phpでclassで定数（const）プロパティを使っても、staticプロパティになりnewで定義したインスタンスから呼び出すことができない

## 修正

```php
class Foo {
     public $a = "aaa";
     public const b = "bbb";
 }
 
 $foo = new Foo();
 echo $foo->a;
 echo "\n";
 echo Foo::b;
```

## 結果

```
aaa
bbb
```

## 補足
インターフェースでは定数プロパティしか定義できず、変数プロパティは定義できない。
私の英語勉強法（ライフハック）

受験英語ではない、大人の英語勉強法について記す。

社会人になるとTOEIC受験が課せられる。
教材を購入して勉強されている方、駅前留学やSkype/Zoomで勉強されている方も多いと思う。
私の英語勉強法を以下に示す。ご参考まで。

>（1）ステーヴン・R・コヴィーの「7つの習慣」の日本語の本と英語の本と音声CD。
　　→CDをiPhoneに入れて、ディクテーション。最初のうちは全く聞き取れない。
（2）American Accent Training 2nd Ed.（CD付き）
　　→CDをiPhoneに入れて、ディクテーション。最初のうちは全く聞き取れない。

全く聞き取れないが、とにかくヘビーローテーションで聞いた。

>（3）Spotifyで「SpeakEnglishPodcast.com」をディクテーション。

この教材はゆっくり話してくれるので問題なく聞き取れる。
また、以下の教材も参考になった。

>（4）Spotifyの「外資系裏技英語」

以上の（1）〜（3）の教材をローテーションでディクテーションした。
疲れた時は、（4）や「武田鉄矢・今朝の三枚おろし」を聞いたりした。

なんとなく聞き取れるようになったので、海外Tech系YouTuberの動画も見るようにした。

>（5）Spotifyで「Lex Fridman Podcast」をディクテーション。

出身はソビエトの方なのですが、低音で流暢な英語を話されます。話し方が好きです。
ここまでくると、英語の勉強というよりは、さまざまな方々のインタビューが聞けるので、
内容の方が面白くなってくる。
AI関連の話やコンピュータ関連の話に興味深々になってきます。

「フレンズ」のDVDも購入したが、内容に興味が湧かないので、パス。
ニュースの記事や動画では、CNNにチャレンジしたが、事件や事故の記事や動画に嫌悪感を覚えたのでこちらもパス。

>（6）BloomBergのライブ

経済関連のニュースなので、基本、嫌悪感はない。画質も綺麗。だけど、土日は手抜き番組。

>（7）Spotifyで「Kalyn’s Coffee Talk」をディクテーション。

くしゃみが入っていたりしますが、綺麗な生の英語が聞けるので大好きなコンテンツです。

ポイントは、

>- 7〜8割理解できたら、次のレベルの教材を自ら探せば良いような気がします。（目の前にニンジンをぶら下げる）
>- 他人が勧める教材でも、自分に合わないと思ったら、パス。（英語の絵本や、古典的な小説を勧められても興味ナシ）

あとは、スピーキングも頑張らないといけません。
ちなみに、ここまで来る間、中国語も勉強してHSKの1級（1番下のレベル）に合格しました。
今は、フランス語にも挑戦中です。:relaxed:

追記：以下もおすすめ。NYSEの情報をゲットできます。無料で。

>(8) Sportifyで「Inside the ICE House」

追記（その２）：現在、ポッドキャストで以下の番組を聞いています。

>- Bloomberg, Bloomberg Technology
>- Bloomberg, Businessweek
>- The Wall Street Journal, WSJ Tech News Briefing
>- The Wall Street Journal, WSJ What's News
>- The Wall Street Journal, The Journal.
>- The New York Times, The Daily
>- ABC News, World News Tonight with David Muir
>- NPR, Up First 

追記（その３）：やはりユーモア交じりのニュース番組がおもしろいよね。YouTubeで検索して動画を視聴しています。

>- SNL
>- The Daily Show
>- The Tonight Show
>- The Colbert Report
Rails PK FK ってなんじゃ？

##テーブル定義でいきなりPK・FKが。。
今回、課題として「このようなテーブルを作成してください」ということで出てきたPK・FK.

##結論
PK = primary_key
FK = foreign_key

のことでした。
ただ、このFKは過去にいわゆる外部キーとして出会ったことがあったものの、PKって何？となり申した。

結論、主キーのことでした。
これは、テーブルを作成した時必ず出てくるidがまさにそれでした。
ただ、これを変える方法もあるんだとか。。

参考資料
https://www.kaqiita.com/entry/2019/02/17/104923

今回の課題ではそのままidのことでしたのでそのままやっていきます。

しかし、なんでも略されるとわけわからなくなる時ありますよね。
・・・まじ最初サッカーやんって⚽️。
【Xcode/Swift豆知識 #1】 「Color Literal」で直感的にカラー指定

##はじめに

Xcode標準搭載のカラーパレット「Color Literal」を使うことで、直感的にUIColorを指定できます。
本記事は、

- コードで色を指定するのが面倒と感じる人
- NavigationBarやTabBarなどの色を直感的に変更したい人

これらに当てはまる人におすすめです！

##開発環境

- Swift5
- Xcode 12.4

##実際のコード

「color...」と打つと、UIColorの候補に**「Color Literal」**が出てきます。

![Color Literal 1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/655655/bffef953-3577-b481-9cf9-e2af48a0b3f2.png)


カラーパレットらしきものに自動で変換されます！
![Color Literal 2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/655655/cfec6035-4693-83ef-6994-0b872f5a15ae.png)

よく使われる色から選択することも・・・
![Color Literal 3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/655655/d8f4f35e-d948-6ad9-88c9-5ed9aacdf475.png)


RGBから色を決めたり、Opacity（透明度）なんかもいじれちゃいます！便利！
![Color Literal 4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/655655/d1063fe8-5086-d405-a280-b40e20621ab0.png)



##最後に

今日はXcode / Swift豆知識その１として、「Color Literal」をご紹介しました。

NavigationBarやTabBarの色を変更したいときは特に便利ですので
ぜひ使ってみてくださいね！

参考記事：[iPhoneアプリのヘッダー（ナビゲーションバー）の色を変更する](https://qiita.com/Gattaca/items/5f85870e624735d272a9)


ここまで読んでいただいて、ありがとうございました。
ハンター・フレームワーク理論とは（ライフハック）

#HFT
##Hunter Framework Theory 
ハンター・フレームワーク理論とは

>- 人類は、狩猟に適した体に進化した。
- 現代におけるさまざまな仕事を、狩猟というフレームワーク（獲物ー狩りー捕獲物、敵ー戦いー勝利）に当てはめて考えると、合致する部分が多いという理論。

すなわち、**「人間は知的生産向けの体を未だ獲得していない」**と言うこと。
**「知的生産をするためには、運動が必要不可欠である」**と言える。

例を以下に示す。
>【狩猟　　：　獲物　　　ー　狩り（運動）ー　捕獲物】
【戦争　　：　敵　　　　ー　戦い（運動）ー　勝利　】
【スポーツ：　対戦相手　ー　対戦（運動）ー　勝利　】
【農業　　：　自然　　　ー　農耕（運動）ー　収穫物】
【製造業　：　製造目標　ー　製造（運動）ー　製造物】
　　　　　　（製造台数、製造コスト低減、品質向上　etc.）


知的生産について考察してみる。知的創造は、運動を伴っていない。なので、狩猟というフレームワークに合致していない。プログラマもこれに含まれる。
>【知的生産：　目標　　　ー　知的創造　　ー　創造物】
　　　　　　　　　　　　　（運動を伴わない）

*知的創造をしている小説家の村上春樹さんやiPS細胞の山中先生は、よく運動しているそうです。*

**サラリーマンは、通勤することで運動している（or 運動していた）のですが、新型コロナの影響で、運動不足になっている方も多いのではないでしょうか。カラダのバランスを崩さないようご自愛ください。**
Nas の共有ドライブをローカルに自動マウント

Nas の共有ドライブをローカルに自動マウントします
####サーバー側

まずは、サーバー側でハードディスクの自動マウントをマニュアル設定にします。

Disks もしくは gnome-disks で編集ができます。

~~~~
gnome-disks ;
~~~~

マウントオプションを編集を選択
![Screenshot from 2021-03-01 03-26-32.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115935/3db4d470-66f2-697b-03ea-d0cc7049c1af.png)
ユーザーセッションのデフォルトを変更
マウントポイントを共有フォルダ名として指定
![Screenshot from 2021-03-01 03-26-43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115935/65e9aba2-daed-373c-3ec0-725cf2e6da6e.png)
それから
エクスプローラー？から /mnt/960GB を開いて
フォルダを右クリックしてプロパティ→ローカルエリア共有を選択して、項目を設定します。
![Screenshot from 2021-03-01 03-27-43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115935/ba3b966f-0588-c399-37ee-1e0c944475a0.png)
ゲストへのアクセスはちょっと分からないです。
おそらくwindowsユーザー向けか何かと思います。

初期設定の場合、samba のインストールがうながされると思いますのでインストールを行います。
####クライアント側

下記コマンドで共有フォルダを置く場所（/mnt/my960GB）と、ネットワークの共有フォルダの場所（//192.168.0.108/960GB）を指定します。
※USERNAMEとPASSWORDは適宜指定してください

~~~~
sudo mkdir -p /mnt/my960GB ;
sudo mount -t cifs -o username=USERNAME,password=PASSWORD //192.168.0.108/960GB /mnt/my960GB ;
~~~~

これで /mnt/my960B にアクセスすると、ネットワーク共有フォルダの中身が見れるかと思います。

ただ、これだけですと、再起動した際に設定が解除されるので /etc/fstab に自動で毎回マウントするように設定を行います。

~~~~bash
sudo gedit /etc/fstab ;
~~~~

※USERNAMEとPASSWORDは適宜指定してください

~~~~bash:/etc/fstab
//192.168.0.108/960GB /mnt/my960GB cifs username=USERNAME,password=PASSWORD,uid=1000,gid=1000,file_mode=0755,dir_mode=0755 0 0
~~~~

再起動すると、/mnt/my960B にネットワークごしでマウントされているかと思います。
あとはお気に入りに入れるなどすれば作業がしやすいかと思います。

もし、うまくマウントができない場合はパーミッションの場合があります。
####参考リンク
- [NASをマウントする: プログラマの歩き方 ](http://zorinos.seesaa.net/article/418671734.html)
- [LinuxでのNASへの自動マウントの方法@2021 | Red Full Moon ](https://red-full-moon.com/automount-to-nas-on-linux/)
【よくある間違いを避ける】For-range ループで意図した値を Goroutine に渡す

## 参考

こちらの動画 ([Concurrency Made Easy (Practical Tips For Effective Concurrency In Go)](https://youtu.be/DqHb5KBe7qI?t=955) を参考にしています。
* コードを少し変えています。

## 問題

下記コードで出力される結果は何でしょうか？

```golang
package main

import (
	"fmt"
	"sync"
)

func main() {
	repos := []string{"aaa", "bbb", "ccc", "ddd"}

	sem := make(chan int, 4)

	var wg sync.WaitGroup
	wg.Add(len(repos))

	for _, repo := range repos {
		go func() {
			defer wg.Done()
			sem <- 1
			fmt.Println(repo)
			<-sem
		}()
	}

	wg.Wait()
	close(sem)
}
```

答えは、

```
ddd
ddd
ddd
ddd
```

です。
## 原因

スコープが __"今" の `range` 値__ となっているから。
for ループが最速すぎて、結果的に、全ての Goroutine が for-range の最後の "ddd" を取得することになっている。
(注意: `for-range` で返ってくる値は、配列の順番通りであることは保証していないので、環境によっては変わる可能性あり)

## 改善方法

無名関数の引数に Goroutine を __実行するタイミングの `range` 値__ を渡す。

```golang
package main

import (
	"fmt"
	"sync"
)

func main() {
	repos := []string{"aaa", "bbb", "ccc", "ddd"}

	sem := make(chan int, 4)

	var wg sync.WaitGroup
	wg.Add(len(repos))

	for i := range repos {
		go func(rep string) {
			defer wg.Done()
			sem <- 1
			fmt.Println(rep)
			<-sem
		}(repos[i])
	}

	wg.Wait()
	close(sem)
}
```

## For-range ループ利用時の注意
`for-range` では 取り出す順番は保証されていません。
また、Goroutine も処理が終了したタイミングで戻ってくるので、意図した通りの順番にはならないケースが多いです。

ちなみに改善後のコード実行結果は、下記のようになりました。

```
bbb
aaa
ccc
ddd
```
<input type="password">でテンキーを表示したいとき

```html
<input type="password">
```
の入力フォームはモバイル端末だとデフォルトでは英数字キーボードが表示されます。

しかし、パスワードを数字に限定したい場合には英数字キーボードは不便です。

<code>input type="number"</code>を使わずにテンキーを表示させるには、inputmode属性を使います。

このinputmode属性を指定することで、type属性にかかわらずデータ型を明示することができます。

今回は数字を入力させたいので

```html
<input type="password" inputmode="numeric">
```

こうするとフォームの入力時にテンキーが出てきます。numericを指定した時のキーボードは０から９までの数字を入力するものです。負号キーを表示するかどうかは端末によります。
※inputmode="decimal"でもできます。

inputmode属性の値はnumericの他にもnone,decimal,text,tel,search,email,urlがあります。

大体type属性で指定できるので使うとすればnoneかnumeric,decimalくらいでしょう。

HTML5.2で一瞬廃止になりましたが割と便利なので復活したようです。
Githubのコードを気持ちよく読めるツール github1s

Githubを読む時はなかなかIDEのような便利な体験ができないといつも思っています。ローカルにコードをCloneしなくてもVSCode風で気持ちよくGithubを読めるツール**Github1s**を紹介したいと思います。
[https://github.com/conwnet/github1s](https://github.com/conwnet/github1s)
##使い方
何もインストールする必要もありません。URLに github.com -> github1s.com に変更するだけ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/533586/7185c1df-18e3-75ed-643a-d4f75291afb8.png)
するとVScode風になります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/533586/5a837036-7f83-0431-f536-3c740783603a.png)
CMD+P でファイル検索もできます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/533586/6ae8b09d-ea09-50ff-dc85-dc582aff1cb4.png)
しかも**全然重くありません**

また、GitHubのAPIを利用しているため、Tokenのない時はかなり厳しいアクセス頻度制限（60 requests/hour）があります。
ここでTokenを作れば、5000 requests/h になるので、快適に使えます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/533586/dbf55328-348e-e911-86f2-7dd6435003b9.png)


##仕組み
便利で興味深いツールですね。仕組みは以下のようです。
>Github1s is based on VS Code 1.52.1 now. VS Code can be built for a browser version officially. I also used the code and got inspired by Code Server.

>Thanks to the very powerful and flexible extensibility of VS Code, we can easily implement a VS Code extension that provides the custom File IO ability using FileSystemProvider API. There is an official demo named vscode-web-playground which shows how it is used.

>On the other hand, GitHub provides the powerful REST API that can be used for a variety of tasks which includes reading directories and files for sure.

>According to the above, obviously, the core concept of GitHub1s is to implement a VS Code Extension (includes FileSystemProvider) using GitHub REST API.

>We may switch to the GitHub GraphQL API for more friendly user experience in the future, thanks to @xcv58 and @kanhegaonkarsaurabh. See details at Issue 12.

>GitHub1s is a purely static web app (because it really doesn't need a backend service, does it?). So we just deploy it on GitHub Pages now (the gh-pages branch of this repository), and it is free. The service of GitHub1s could be reliable (GitHub is very reliable) because nobody needs to pay the web hosting bills.

公式のVSCodeのブラウザ版をベースにして、そしてFileSystemProvider APIでGitHubのAPIと連携しているようです。暇の時に詳しく読んでみるかな。

以上
[js] 文字列への変換にnew String()を使うのはよくない

こんなコードを見かけた

```js
console.log('price = ' + new String(price));
```

数値から文字列の変換に`new String`を用いている。

実はこのnew Stringが返すのはstringではなく`stringっぽい何か`なのだ！

```js
const s = '100';
const s2 = new String(100);
console.log(typeof s); // string
console.log(typeof s2); // object
```

実は`new String`が返すのはstringのボックス型なのだ。似たような振る舞いをするが決してstringではない！
=== undefined よりも == null を使おう

以下のコードを見てくれ

```js
const data = await fetchData( ... );
if (data.flag === undefined) {
  ...
}
```

`=== undefined` を使っているがそれは意図して使っているのか？

`== null` と `=== undefined`には以下のような違いがある

### `== null`

null もしくは undefined と一致

### `=== undefined`
undefinedと一致


つまりnullはOK！undefinedはダメ！という状況でしか使わないのだ！
いつ紛れ込むかわからないnullのことを考えると `== null`を使うのが吉だ！
mDNS名を追いかけてMQTTで何かを投げつけるボタン

##RaspberryPiをシャットダウンorリセットするのに最適
Raspberry Piが再起動してIPアドレス変わった場合、ちゃんとIPアドレスを追いかけるようにした。

・追加したノードノード（うろ覚え）
node-red-contrib-rpi-shutdown
node-red-contrib-aedes

・いい感じにnode-REDを作っておく
![スクリーンショット 2021-03-01 2.47.38.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/181687/3fa4b98a-0a62-2df6-14e3-477d99cd7846.png)
トピック名はtopic

##参考資料
https://qiita.com/hanapage/items/c2df143dbde33e03e674
https://qiita.com/poruruba/items/5d9434aec4895f8a6f7a

##ソース
<details>
<summary>m5atom-MQTTswith</summary>
<div>

```m5atom-MQTTswith.ino
#include <M5Atom.h>
#include <WiFi.h>
#include <PubSubClient.h>
#include <ESPmDNS.h>

WiFiClient wifi;
const char* wifi_ssid = "Wi-Fi";
const char* wifi_password = "pass";

PubSubClient client(wifi);

//.local不要
const char* mqtt_server = "your Raspberry Pi mDNS name";

const uint16_t mqtt_port = 1883; 
#define MQTT_CLIENT_NAME  "M5Atom"

#define BTN_PUSH_MARGIN 100
#define MQTT_BUFFER_SIZE 512

bool pressed = false; 

void wifi_connect(void){
  Serial.print("WiFi Connenting");

  WiFi.begin(wifi_ssid, wifi_password);
  while (WiFi.status() != WL_CONNECTED) {
    Serial.print(".");
    delay(1000);
  }
  Serial.println("");
  Serial.print("Connected : ");
  Serial.println(WiFi.localIP());

}

void sendMessage(void){
  // MQTT Publish
  client.publish("topic","1");
  delay(BTN_PUSH_MARGIN);
  client.publish("topic","0");
}

void setup() {
  M5.begin(true, false, true);

  Serial.begin(115200);
  wifi_connect();
  if(!MDNS.begin("m5atom")){
    Serial.println("Error MDNS");
    while(1){
      delay(1000);
    }
  }
  client.setBufferSize(MQTT_BUFFER_SIZE);
}


void loop() {
  client.loop();
  while(!client.connected() ){
    if (MDNS.queryHost(mqtt_server)==IPAddress('0.0.0.0')){
      delay(1000);
    }
    IPAddress mqtt_server_ip = MDNS.queryHost(mqtt_server);
    Serial.println(mqtt_server_ip);
    client.setServer(mqtt_server_ip, mqtt_port);
    Serial.println("Mqtt Reconnecting");
    if( client.connect(MQTT_CLIENT_NAME) ){
      Serial.println("Mqtt Connected");
      break;
    }
    delay(1000);
  }

  M5.update();

    if (M5.Btn.isPressed() && !pressed ){
      pressed = true;
      // 送信
      sendMessage();
      Serial.println("Mqtt Send");
      delay(BTN_PUSH_MARGIN);
    }else if( M5.Btn.isReleased() && pressed ){
      pressed = false;

      delay(BTN_PUSH_MARGIN);
    }
}
```


</div>
</details>
価値のないコメント

最近見かけたコメントで微妙なコメントを紹介する。

## 英語 -> 日本語なコメント

```tsx
enum Items {
  Apple, // りんご
  Banana, // バナナ
  Orange, // オレンジ
}

```

こういうコメントが生まれる理由を考察するに、

①とりあえずコメントを書こう！
②何かいていいかわからない
③日本語訳書いておけばそれっぽいNE!

という感じなのかな？

こういうコメントは価値がないくせに満足感を与えるので危険です。
メディエーターパターンは神

API上のコードとjs上の列挙体の値とラベル文字列の値の３要素がある。

```ts
enum MessageStringCode {
  PowerOn = '01',
  PowerOff = '02'  
}

enum MessageType {
  PowerOn,
  PowerOff,
}

enum MessageLabel {
  PowerOn = 'パワーオン',
  PowerOff = 'パワーオフ'
}
```

これらを相互変換するために以下の関数を定義する。

```ts
function stringCodeToType(a, b) { ... }
function stringCodeToLabel(a, b) { ... }
function typeToStringCode(a, b) { ... }
function typeToLabel(a, b) { ... }
function labelToStringCode(a, b) { ... }
function labelToType(a, b) { ... }
```

# FUCK!!!

もう一度言おう

# FUCK!!!

# メディエーターパターンを使おう

https://www.techscore.com/tech/DesignPattern/Mediator.html/

詳しくはこれ見てちょ

メディエーターパターンを使えば定義する関数の数が圧倒的に減る

```ts
function stringCodeToLabel(a, b) { ... }
function typeToLabel(a, b) { ... }
function labelToStringCode(a, b) { ... }
function labelToType(a, b) { ... }
```

変換関数をLabel経由に集約してstringCode -> Type へ変換したい場合は stringCode -> Label -> Type のように変換する

何が言いたいかというと、全てを一つのものに集約する形で実装しようってことです。

# おわり

デザインパターンは絶対に役に立つ日が来るので勉強しよう
Ubuntu に python の opencv をインストール

Ubuntu に python の opencv をインストールします。

なにやら OpenCV の sift が普通に使えるようになったからインストールしてみました。

[SIFTの特許が切れてOpenCV v4.4.0から普通に使えるようになってた話 - Qiita ](https://qiita.com/herr-shigeo/items/ec9abac4212628162598)

ただし、2021年3月1日現在、下記でインストールされるバージョンは 4.2 になります。

今来た３行向けの方

~~~~bash
# pip3 install
sudo apt update ;
sudo apt install python3-pip ;
pip3 --version ;

# opencv install ;
pip install opencv-python ;
pip install opencv-contrib-python ;
dpkg -l | grep libopencv ;
~~~~

####参考リンク
- [pip で OpenCV のインストール - Qiita ](https://qiita.com/fiftystorm36/items/1a285b5fbf99f8ac82eb)
- [インストールされたOpenCVのバージョンを確認するコマンド - 動かざることバグの如し]( https://thr3a.hatenablog.com/entry/20190525/1558764423)
- [How to Install Python Pip on Ubuntu 20.04 | Linuxize ](https://linuxize.com/post/how-to-install-pip-on-ubuntu-20.04/)
Reactプロジェクトで this.hoge.bind(this) とかやってる人に言いたい

これを見てくれ

```ts
class CoolButton {
  constructor() {
    this.onClick.bind(this);
  }

  onClick() {
    ...
  }

  render() {
    return <button onClick={this.onClick}>Cool</button>;
  }
}
```

このbindを見て疑念を抱いた君、正解だ
イベントハンドリング部分でアロー関数でイベントを書くようにすればこんなthisは要らない

```ts
class CoolButton {
  onClick() {}

  render() {
    return <button onClick={() => this.onClick()}>Cool</button>;
  }
}
```

## 結論

onHogehoge のようなイベントはアロー関数で指定してあげよう
typescriptでUtils.hogeのような関数群を束ねるオブジェクトの作り方

便利な関数をUtilsというオブジェクトにまとめてエクスポートする場合の3種類の書き方を紹介する。

### オブジェクト

```ts
export const Utils = {
  getVersion: () => {
    return '1.5.4';
  },
  getSetting: () => { ... }
};
```

- メリット: TS初心者でもわかりやすい書き方
- デメリット: プロパティの再代入ができてしまう

### 匿名クラス

```ts
export const Utils = new class {
  getVersion() {
    ...
  }

  getSetting() { ... }
}();
```

- メリット: メンバ変数やアクセス修飾子が使える。再代入できない。
- デメリット: あまりなじみのない書き方なのでTS初心者には苦

### 名前空間

```ts
export namespace Utils {
  export function getVersion() { ... }
  export function getSetting() { ... }
}
```

- メリット: かっこいい。再代入できない。
- デメリット: exportをたくさん書く。namespaceが利用できない環境がたまにある。

## おわり

おすすめは名前空間です。かっこいいので
React Hookが何かをかいつまんで昨日の自分に教える

昨日の自分よ、見てるか～‘？

参考: https://ja.reactjs.org/docs/hooks-intro.html

関数コンポーネントにステートを導入できる機能みたいだ。導入された理由の一つにビジネスロジックの分離？があるみたいだが理屈がよくわからないのでいったん忘れてよい。

## sample code

```js
import React, { useState, useEffect } from 'react';

function Example() {
  const [count, setCount] = useState(0);

  // Similar to componentDidMount and componentDidUpdate:
  useEffect(() => {
    // Update the document title using the browser API
    document.title = `You clicked ${count} times`;
  });

  return (
    <div>
      <p>You clicked {count} times</p>
      <button onClick={() => setCount(count + 1)}>
        Click me
      </button>
    </div>
  );
}
```

`const [count, setCount] = useState(0);`

countはステート変数
setCountはステートを変更する関数のようだ

`useEffect` はステート変更時のイベントをかけるみたい。

## おわり

setState とかの新しい書き方ってこと？
fishでPowerlineをwsl2上で設定する方法，

#fish install

まずはfishをinstallする．ubuntuなら，

```
sudo apt upgrade 
sudo apt update
sudo apt install fish
```
次にinstallしたらfishのパスを確認し，デフォルトのシェルに変更する．

```
which fish
chsh -s /user/bin/fish
```

設定ファイルなどは以下のディレクトリにある．
```
.config/fish
```

#パッケージマネージャのinstall

fishermanの場合

```
curl https://git.io/fisher --create-dirs -sLo ~/.config/fish/functions/fisher.fish
```

プラグインpeco と zを入れてる．

```
fisher install oh-my-fish/plugin-peco
fisher install jethrokuan/z
```

```:~/.config/fish/config.fish
# ---
# peco
# ---
function fish_user_key_bindings
    bind \cr peco_select_history
end
```

Powerlineのプラグインを入れてみる．

```
fisher add oh-my-fish/theme-bobthefish
```
これを入れるとコンソールの見た目が変わる．ところが，文字化けが発生するためPwerline-fontsをインストールする必要がある．

任意の場所でフォントをインストールする．

```
git clone https://github.com/powerline/fonts.git
cd fonts
./install.sh
cd ../
rm -r ./fonts
```

（注意）
これでフォントが設定できるになるはずだが，うまくいかないならgit-hubに公開されているPowerline-fontをダウンロードして右クリでインストールすれば，おなじみのWSLフォント設定画面から設定できます．Notoなど様々なフォントがある．

ブランチを表示させる設定を明示する．

```:~/.config/fish/config.fish
set -g theme_display_git_master_branch yes
```
を追記して，fishを再起動させる，

そのほかにも

```
# ----------
# bobthefish config
# ----------
set -g fish_prompt_pwd_dir_length 0  # ディレクトリ省略しない
set -g theme_newline_cursor yes  # プロンプトを改行した先に設ける
set -g theme_display_git_master_branch yes  # git の branch 名を表示
set -g theme_color_scheme dracula
set -g theme_display_date no  # 時刻を表示しないように設定
set -g theme_display_cmd_duration no  # コマンド実行時間の非表示

```

#参考
以下のサイトを参考にしました．

https://qiita.com/sugimount/items/ff80f9ba481ec81b5600

https://qiita.com/sudachi0114/items/988278c9dc11b92867b5


https://qiita.com/sugimount/items/ff80f9ba481ec81b5600
[js] 指定したPromiseが解決されるまでローディング表示

## 概要

![a.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/731232/978824e4-a9a1-f4b0-e27e-bfe6035439ea.gif)


Promiseを渡すとそれが解決されるまでローディング表示をする関数を実装する。

### ローディング関数の仕組み

1. 最初にローディング表示する
2. 渡されたPromiseが解決されたらローディング表示を解除する

### Promiseの解決を検知する方法

渡されたPromiseに対してthenメソッドを呼び出すことでPromiseが解決されたことを検知できる。

```js
promise.then(() => console.log('解決された'))
```

### 実装

```js
function loading(promise) {
  let i = 0;
  const interval = setInterval(() => {
    showLoading(((++i) % 3) + 1);
  }, 500);
  promise.then(() => {
    clearInterval(interval);
    endLoading();
  });
}
```

### デモ

https://stackblitz.com/edit/js-4ffnh3?file=index.js
ブロックチェーン関連ページ

個人的によく参照するブロックチェーン関連ページのリンク集です。

* [Bitcoin wiki](https://en.bitcoin.it/wiki/Main_Page)
* [Ethereum wiki](https://github.com/ethereum/wiki/wiki)

* [Bitcoin core](https://github.com/bitcoin/bitcoin)
* [go-ethereum](https://github.com/ethereum/go-ethereum)
1.3. Windowsドライブマウント設定

# 概略
WSLではデフォルトでCドライブを``/mnt/c``に起動時に自動でマウントしていますが、Cドライブ以外のドライブもマウント可能です。仕事でファイルサーバを使用している場合はネットワークドライブに割り当ててWSLにマウントすると便利です。
下記のようなイメージになります。
![WSL-WinDriveマウント図](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/96681/d44d7729-ff40-3d01-bcd8-0db7aacfa432.png)
コンソールから操作しなくてもWindowsのExplorerの方が操作しやすいと思うかもしれませんがコンソールから操作できるとShellやプログラム中からWindowsドライブが使用でき非常に便利になります。

# ドライブの自動マウント設定
Windows「C:」以外のドライブをマウントします。ここではFドライブをマウントします。
WSLでは内部ドライブは自動マウントされますが、他のWindowsドライブは、fstab に記載しておく必要があります。
Windowsドライブは/etc/wsl.conf で制御できるようになっています。

#### 1./etc/wsl.conf設定

```console:wsl.conf
$ sudo vim /etc/wsl.conf
```

下記の通り設定してください。

```configuration:wsl.conf
[automount]
enabled=true                # Cドライブなどの DrvFs の自動マウントする
mountFsTab=true             # WSLの起動時に /etc/fstab を読み込んで自動的にマウントする
root="/mnt/"                # DrvFsのマウント先
options=""                  # DrvFsのマウントオプション
                            # 規定値: "uid=1000,gid=1000,umask=000,fmask=000,dmask=000"
crossDistro=true            # ディストリビューションを跨いだマウントをサポートする (ver2004以降)

[network]
generateHosts=true          # /etc/hosts を自動生成する
generateResolvConf=true     # /etc/resolv.conf を自動生成する

[interop]
enabled=true                # WSL内からWindowsプログラムの起動をサポートする (ver1809以降)
appendWindowsPath=true      # WSL内のPATH環境変数に、WindowsのPATH環境変数を追加する (ver1809以降)

[user]
default="develop"           # 規定のログインユーザ名を指定する (ver2004以降) 規定値: レジストリ値に従う

[filesystem]
umask=0022                  # デフォルトのパーミッションを指定する (ver2004以降)
```

#### 2./etc/fstab設定
次に/etc/fstabを設定します。

```console:/etc/fstab
$ sudo vim /etc/fstab
```

ファイル末尾に下記の行を追記します。
例)マウント元windows側ドライブ「f:」、マウント先Linux側ドライブ「/mnt/f」の場合

```bash:/etc/fstab
# network drive
f: /mnt/f drvfs metadata,noatime,uid=1000,gid=1000,defaults 0 0
```

#### 3.マウントディレクトリ作成

```console
$ sudo mkdir -p /mnt/f
$ sudo chown -R develop:develop /mnt/f
$ sudo chmod -R 777 /mnt/f
```

#### 4.確認
マウントしてみてください。

```console
$ sudo mount -a
$ ls -la /mnt/f
```

---

[1.2.ConEmu・Nyagosインストール・設定](https://qiita.com/boss_ape/items/015feebc6e3a77311e01) < 前 **1.3.Windowsドライブマウント設定** 次 > [1.4.Google Driveマウント設定](https://qiita.com/boss_ape/items/74bcad7441417c331205)
TextField入門

FlutterでTextFieldのUIを整える作業を行ったので、備忘録的に残しておきたい。


```
TextField(
  style: TextStyle(
     color: Colors.black,
   ),
  decoration: InputDecoration(
    filled: true,
    fillColor: Colors.white,
    icon: Icon(Icons.email, color: Colors.white),
    hintText: 'ヒントテキスト',
    hintStyle: TextStyle(
      color: Colors.grey,
    ),
    border: OutlineInputBorder(
      borderRadius: BorderRadius.all(
        Radius.circular(10.0),
      ),
   borderSide: BorderSide.none,
    ),
  ),                
),
```



![スクリーンショット 2021-03-01 1.23.12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/998564/db091d8e-b12b-bfba-fe4e-ab45089e53f2.png)
SIFTの特許が切れてOpenCV v4.4.0から普通に使えるようになってた話

## はじめに
最近、OpenCVを意図せずアップデートしたところ、SIFTを使っているコードで警告が表示されました。その原因は、SIFTの特許が切れて普通に使えるようになったためでした。その時の備忘録です。

## 開発環境
Ubuntu 18.04.4 LTS
Python 3.6.9
opencv 4.5.1
dlib 19.21.1

## 遭遇した警告
OpenCV 4.5.1で以下コードを呼び出したところ

```python
sift = cv2.xfeatures2d.SIFT_create()
```
以下の警告が出ました。

```python
[ WARN:0] global /tmp/pip-build-uyw1ttra/opencv-contrib-python/opencv_contrib/modules/xfeatures2d/misc/python/shadow_sift.hpp (15) SIFT_create DEPRECATED: cv.xfeatures2d.SIFT_create() is deprecated due SIFT tranfer to the main repository. https://github.com/opencv/opencv/issues/16736
```
警告に表示されている[リンク](https://github.com/opencv/opencv/wiki/GSoC_2020#idea-better-sift-in-the-main-repository)を確認すると、以下の記載がありました。
>Description: In 2020 March the patent on one of the most popular feature detection algorithm, SIFT, expires. So, we can move the implementation from opencv_contrib/xfeatures2d to the main OpenCV repository (opencv/features2d) in the late spring or summer. We can also optimize and improve it further, probably create bit-exact implementation.

OpenCV 4.4.0の[リリースノート](https://opencv.org/opencv-4-4-0/)に以下の記載がありました。
>SIFT (Scale-Invariant Feature Transform) algorithm has been moved to the main repository (patent expired)

### OpenCV 4.4.0での呼び出し方
xfeatures2dをネームスペースで指定する必要がなくなり、以下のように呼べ出せるようになりました。

```python
sift = cv2.SIFT_create()
```
### まとめ
オープンソースなのに特許を気にするのは煩わしいですが、OpenCV使用時の煩わしさが１つ減りました。
GitHubのデフォルトブランチがmasterからmainへ変更した影響

# 概要
事の発端は[こちらの記事](https://github.com/github/renaming)
端的に説明するとGitHubのリポジトリ作成時、デフォルトが`master`から`main`に変更されていた。

# 事象
HerokuへのデプロイをAPI経由で行う際、ブランチを指定するがそれに影響が出た。
ブランチ変更の影響でmasterを指定するとデプロイできていない。

直接打つ場合は`$HEROKU_API_KEY`, `$HEROKU_APP_NAME`は任意の名前に変更。

```
# デプロイできている
git push https://heroku:$HEROKU_API_KEY@git.heroku.com/$HEROKU_APP_NAME.git main
# デプロイできていない
git push https://heroku:$HEROKU_API_KEY@git.heroku.com/$HEROKU_APP_NAME.git master
```

色々な記事では末尾の`main`部分を`master`をして記述しているが`master`でpushをすると失敗する。
(独自でmasterブランチを作成したり昔作成したリポジトリ[masterがデフォルト]なら問題ないと思う)

まあそもそも構文の意味をちゃんと理解すればそこまでハマることもないと思うが問題は次だ。

**CircleCIからHerokuへのpush時ブランチ指定を間違えても正常に動いてる(ように見えてしまう)のが問題**
下記画像はCircleCIからHerokuへデプロイするjobだがこれ自体は成功しているがデプロイは出来ていない。
![deploy_succsess(のように見えるが失敗している).PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1159336/7c45f44d-c563-4d14-afcd-abcf5e281cdd.png)

原因は前述したとおりブランチ指定を`master`にしているため。
**事態をややこしくしたのはCIrcleCIのjobは成功しているのにデプロイは失敗してるため何が悪いのか皆目見当がつかない点。**
つまりjobは成功しているから原因はここではないと考えてしまい、余計にものすごい遠回りをしてしまった。
そしてブランチ指定をmainに変更するとjobが失敗するので(それはまた別の要因)ややこしさが加速した。
mainに指定したのは間違っているのでは？と誤った考え方に推移していった。。。

# 解決策
これも前述したとおりブランチ部分をちゃんと`main`に変更すれば問題なく動作する。
(しかしmainに変更したとこでまた別の問題が発生して大変な目にあったがそれは別記事に記す。)

# 所感
そもそもデフォルトブランチが`master`ではなく`main`に変わっていたのは、
ネットニュースでちらほら見かけていたのでそこまで驚きはしなかった。
変更した経緯について詳細は省くが自分で動かすときはちゃんと意識しないと変にハマる。

特に単独で失敗するならまだしも色々な環境を経由してコマンド実行するとなると、
どこに原因が潜んでるかの切り分けが困難になるためある程度あたりを付けておくのは大事だなと感じた。
Azure/azure-iot-arduinoをESP32(M5ATOM Lite)で動かしてみる

## はじめに

https://github.com/Azure/azure-iot-arduino

Azure IoT Hub の SDK が公式から提供されています。
しかも、ESP32 に対応したサンプルも含まれています。

サンプルを動かすまでにいくつかステップを踏む必要があったので、解説します。

## 用意するもの

- ESP32 が乗った開発ボード（筆者は[M5ATOM Lite](https://www.switch-science.com/catalog/6262/)を使用）
- Arduino IDE (1.8.13)
- python3 (3.9.2)

## インストール

以下のライブラリのインストールが必要ですので、Arduino IDE からインストールしておきましょう。
 
- `AzureIoTHub`
- `AzureIoTSocket_WiFi`
- `AzureIoTHubMQTTClient`
- `AzureIoTProtocol_MQTT`

## 準備

## スケッチ例を開く

スケッチ例から`iothub_ll_telemetry_sample.ino`を開きます。
<a href="https://gyazo.com/d249be3c3587a57c3e924c1a51c7349b"><img src="https://i.gyazo.com/d249be3c3587a57c3e924c1a51c7349b.png" alt="Image from Gyazo" width="963"/></a>

https://github.com/Azure/azure-iot-arduino#esp32 の通りに設定を進めます。
いくつかピックアップして説明します。

### iot_config.hの設定

`DEVICE_CONNECTION_STRING`には、IoTHub ポータルの IoT デバイスから取得できる`プライマリ接続文字列`を記入します。
<a href="https://gyazo.com/1a8b1e39a59f55b65088beb1c4c9a82f"><img src="https://i.gyazo.com/1a8b1e39a59f55b65088beb1c4c9a82f.png" alt="Image from Gyazo" width="958"/></a>

### platform.txtの設定

`platform.txt`なるテキストファイルを編集する必要があります。
Python で書かれた設定ツールが提供されていますので、遠慮なくそちらを利用しましょう。

https://github.com/Azure/azure-iot-pal-arduino を clone します。

https://github.com/Azure/azure-iot-pal-arduino

`azure-iot-pal-arduino/build_all/base-libraries/AzureIoTHub/src/scripts`に`automate_board_config.py`があるので、実行します。

```bash
python3 automate_board_config.py
```

いくつか選択肢を選びますが、基本`Y`を入力すれば OK です。
自動でバックアップも取ってくれるので安心。

## ESP32に書き込む

`iothub_ll_telemetry_sample.ino`を ESP32 に書き込んでみましょう。
無事書き込めました！
<a href="https://gyazo.com/8f33d13fb9dedba681bad63ff551a45e"><img src="https://i.gyazo.com/8f33d13fb9dedba681bad63ff551a45e.png" alt="Image from Gyazo" width="962"/></a>
（ログに Error がいくつか表示されるのが気になりますが...それはまた別記事にします）。

## おわりに

`AzureIoTSocket_WiFi`がインストールされていないのに気付かず地味にハマりましたが、これで ESP32 で IoTHub を利用する準備が整いました。


## (03/01追記)ハマったところ

### fatal error: internal/blob.h: No such file or directory

GitHub に Issue がありました。[blob.h is missing #9](https://github.com/Azure/azure-iot-pal-arduino/issues/9)
`platform.txt`の設定がうまくできてないのが原因のようですので、 [platform.txtの設定](https://qiita.com/tmitsuoka0423/items/182b29b36e021724dcbc#platformtxt%E3%81%AE%E8%A8%AD%E5%AE%9A)を再度実施しましょう。
（なにかのタイミングでリセットされたらしく、筆者は二度実行しました）
【JavaScript】 海外Teck系YouTuberを真似てみた！(part 4) Blog App | React JS

#１，はじめに
この記事は、海外Teck系YouTuberの動画を参考に、同じプロジェクトを作成してみたものになります！
簡単にですが、動画を通して学べた技術や知識をまとめました！

今回の完成品は、下記に載せています:bangbang:

#２，学んだこと
Reactに必要な、RouterやHookについて学ぶことができました！
JSONサーバーのビルド方法や、Fetchを使ってサーバーと接続する方法も知れました！

#３，参考動画
https://youtube.com/playlist?list=PL4cUxeGkcC9gZD-Tvwfod2gaISzfRiP9d

#４，完成:tada:
![2021-03-01_00h23_36.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/654025/f685d609-e8d7-0184-4826-f49550ace95c.gif)
CircleCIからHerokuへのログインが必要なかった

# 概要
- GitHubへpushするとCircleCIが動作しHerokuへデプロイする仕組みを製作中にハマった。

# 事象
- CircleCIからHerokuへログインするのが失敗したとエラーメッセージが出た。

```
remote: !	WARNING:
remote: !	Do not authenticate with username and password using git.
remote: !	Run `heroku login` to update your credentials, then retry the git command.
remote: !	See documentation for details: https://devcenter.heroku.com/articles/git#http-git-authentication
fatal: Authentication failed for 'https://heroku:@git.heroku.com/.git/'
```

![CircleCI_to_Heroku_push_miss.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1159336/5c14089a-81fd-153e-c3e6-9b5097d93973.png)

# 対処法
そこでHerokuへのログイン認証が失敗していると思い`.circleci/config.yml`に下記記述を追加。

```..circleci/config.yml
jobs:
  deploy:
    executor: heroku/default
    steps:
      - checkout
      - heroku/install
      - run: heroku login # Herokuにログインする処理を追加
      - heroku/deploy-via-git:
          only-branch: main

```

すると下記エラーが発生

```
Error: Cannot log in with HEROKU_API_KEY set
```

![CircleCI_to_Heroku_login_miss.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1159336/736588ea-eaca-d1cb-e981-6d969043ff48.png)

[こちらの記事](https://myownpace.netlify.app/circleci_heroku_doesnot_work/)を参考にAPIキーを再発行して挑戦。
しかし失敗。。。

# 解決策
結論としては`- run: heroku login `を削除したら問題なく動いた。
エラーメッセージの`Run heroku login`とは何だったのか。。。

# 所感
言われてみれば確かにCircleCIからHerokuへ認証ってどうやっているんだろうと不思議に思い
認証を頑張っていたがなぜか一向に成功せず。
ダメもとで一旦ログイン処理を削除したらなぜか後続の処理が動作した、
ここら辺の仕組みがどうなっているかさっぱり謎だがとりあえず動いたのでまあよし(現場猫)
【Xcode】CounterpartSuffixesを設定してファイル移動をちょっと楽にする

## はじめに

Xcodeでは、ファイルにCounterpart（=対の片方）という概念があります。
デフォルトでは、実装ファイルとヘッダファイルがこの関係にあたります。

## Jump to Counterpart

Counterpartへのジャンプは、以下のいずれかで可能です。

- **Navigate > Jump to Next/Previous Counterpart**
- **Ctrl + Command + ↑** or **Ctrl + Command + ↑**
    - 現在のエディタ上で移動
- **Ctrl + Option + Command + ↑** or **Ctrl + Option + Command + ↑**
    - 隣のエディタ上で移動

---

`ViewStream.swift`（左）を開いた状態で **Ctrl + Option + Command + ↑** を押すと、隣のエディタで`ViewStream.swift（Interface）`（右）が開かれます。
![スクリーンショット 2021-02-27 11.19.32.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/190870/e4bcd759-3578-ff9b-d2c2-b81c8a6122a9.png)

## Counterpartの設定

Counterpartは`defaults`コマンドによって、カスタマイズすることが出来ます。

```bash
$ defaults write com.apple.dt.Xcode IDEAdditionalCounterpartSuffixes -array-add "ViewController" "ViewStream" "ViewDataSource"
```

```bash
$ defaults read com.apple.dt.Xcode IDEAdditionalCounterpartSuffixes
(
    ViewController,
    ViewStream,
    ViewDataSource
)
```

（設定を反映させるためには、Xcodeを再起動が必要です。）

この状態で `Ctrl + Command + ↓` を繰り返した場合、ファイル遷移は以下のようになります。

```
ViewController
↓
ViewStream(Interface)
↓
ViewStream
↓
ViewDataSource(Interface)
↓
ViewDataSource
↓
ViewController(Interface)
↓
ViewController // 1周
↓
...
```

## リセット

```bash
$ defaults delete com.apple.dt.Xcode IDEAdditionalCounterpartSuffixes
```

## 最後に

途中インターフェースが表示されるのが微妙ですが、慣れれば便利そうです。
プロジェクト内でアーキテクチャやファイルの命名規則が定まっていると、より効果を発揮しそうです。

## 関連リンク

- https://twitter.com/peterfriese/status/1364544309878534144?s=20
- https://github.com/abema/abema-ios-tutorial-public