OmniAICreator/Qiita-1.07M huggingface dataset:
【MySQL】M1 mac linux ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (38)

自分でも驚くくらい凡ミスで悩んでいたためメモ。

mysqlを起動させようとスタートすると、エラー文字。

```
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)
```

とりあえず、/tmpディレクトリ配下にmysql.sockを作成。

```
cd /tmp/
touch mysql.sock
```

アクセス権限をオールクリア

```
chmod 777 mysql.sock
```

すると()の中が2から38に変わった。

```
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/tmp/mysql.sock' (38)
```

しかし、よく似た記事を発見。
その記事では、

```
mysql.server start
```
を飛ばしていたとのこと。
自分のコマンドを見直すと、

```
mysql　server.start
```
になっていた。

mysqlでERROR 2002 (HY000)のエラーが出たら、
もしかしたらいつもと違うことをやっているだけの可能性がある
ということを疑っても良いかもしれない。
RedashでCSVファイルを読み込ませる(インポートする)

#やりたいこと
Redash上でpostgreSQLを利用しているのですが、手元にあるCSVファイルをどうしてもDB上に結合させたい。
イメージとしては既に使っているDB上に新たなテーブルデータを追加したいという訳です。



結果的にはCSVファイルをDB上に直接的に格納することができずに間接的な方法でしかできなかったです。


#この記事に書いてあること

1. CSVファイルをRedash上に読み込ませる方法
2. そのデータを既存のDBと結合させる方法


**2に関してはスマートなやり方がわからず無理矢理結合させているのであまり参考にしない方がいいと思います。**
(もし他にいいやり方がわかる方がいればご教授頂きたいです..)


#CSVファイルをRedash上に読み込ませる方法
基本的には公式ドキュメントに書いてありますが、色々とつまづいた部分があったので改めて書きます。
https://redash.io/help/data-sources/querying/csv-files


まずRedashではCSVファイルを**アップロードすることはできません**。
代わりにクラウドなどからCSVファイルを読み込むことによってRedash上に格納することができます。


###Step1 データソースを追加する
Redashで```CSV```と```Query Results```というデータソースを用意する必要があります。

データソースCSVでは```1. CSVファイルをRedash上に読み込ませる方法```
データソースQuery Resultsでは```2. そのデータを既存のDBと結合させる方法```
に使用します。



追加方法はSetting -> Data Sources -> New Data Sourcesから追加できます。
NewDataSourcesを押すとプルダウン形式で様々な項目が出ると思うので、CSVとQueryResultsそれぞれ二つ作ってください。
名前はなんでもいいはずですが、公式では一般的にCSVはCSV, QueryResultsはQR とするのが良いとされています。


※**データソースは管理権限アカウントでしか設定できません**。管理権限以外のアカウントだとSettingが表示されません。


###Step2 CSVファイルを読み込ませるためのURLを発行する
先述したとおりRedashでは直接的にCSVファイルをアップロードすることができず、共有URLを介してCSVファイルを読み込む形になります。
使えるプラットフォームはDropbox, GoogleDrive, OneDrive, Github となっています。

ここでは代表的にDropboxによる読み込ませ方を紹介します。他のものに関しては公式ドキュメントを参考にしてください。
(GoogleDriveだと何故か綺麗なテーブルデータとして読み込んでくれなかった..)


※1行目をヘッダーとして認識するため、CSVファイルはヘッダー込みのファイルを用意した方がいいです


###Dropbox
まずCSVファイルをDropboxにアップロードします。

次にそのファイルを共有できる設定にしてリンクをコピーします。

DropBoxのリンクの構造は以下になっていると思います。
```https://www.dropbox.com/s/識別子/ファイル名.csv?dl=0```

このURLを読み込ませる用のURLに変換しなくては行けないので
www.dropbox.com -> dl.dropboxusercontent.com
に変換させます。

なので最終的なURLは
```https://dl.dropboxusercontent.com/s/識別子/ファイル名.csv?dl=0```
になると思います。


###Step3 発行したURLをRedash上で読み込ませる

Top -> Create -> NewQuery　にしてプルダウンリストからCSVを選択
![スクリーンショット 2021-06-08 22.43.50.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/218168/e8cb2143-e60d-a87c-4cb7-5b5fbaa63030.png)

そしてクエリを書く部分に先ほど作成した```https://www.dropbox.com/s/識別子/ファイル名.csv?dl=0```を貼り付けてExecute


するとテーブルデータが下に表示されると思います。
うまく表示されたらSaveを押してクエリを保存。




###Step4 QueryResultsでクエリをキャッシュする

Top -> Create -> NewQuery　にしてプルダウンリストからQueryResults(QR)を選択

クエリを書く部分に

```sql

SELECT * FROM query_クエリID

```
と入力して実行します。
クエリIDの部分には、Step3で保存したクエリにURLの部分の数字列がクエリIDに当たります。
ex) ``https://app.redash.io/~~~~~/queries/791429``←ここ




実行した段階でクエリがキャッシュされるはずなので、次に

```sql

SELECT * FROM cached_query_クエリID

```
として実行します。先ほどと同様の結果が得られれば成功です。

これでCSVファイルがRedash上に保存された状態になると思います。

#2. そのデータを既存のDBと結合させる方法
こちらに関して全くスマートではないですが一応書いておきます。

###Step1 既存のDBの結合させたいデータをCSVファイルにする
プルダウンリストを既存のDBに戻して、結合させたいテーブルデータを

```sql

SELECT * FROM 結合させたいデータ

```

として出力して右下ら辺のボタンからCSVファイルとして書き出せるのでそこでエクスポートします。


###Step2 エクスポートしたCSVファイルを再度1の手順を行う
CSVファイルを1の手順を再度行なってキャッシュさせます。

既存DBデータをキャッシュさせたら先ほどの結合させたかったCSVファイルとJOINさせます

```sql

SELECT * 
FROM cached_query_222 (←既存DBのデータ)
JOIN cached_query_111 (←元々結合させたかったCSVファイル)
ON ~

```


これで既存DBとの結合ができると思います。


かなり強引な方法だと思うのでもう少し便利なやり方があると嬉しい..
PostgreSQL:PostGisを使って座標から情報を取得

座標データから、PostGISに格納している地域情報を取得するQueryの覚書です。

データの用意の方法は省略します。

```SQL
SELECT * FROM TABLE_NAME
WHERE ST_Covers(
	geog, 
	ST_GeogFromText('POINT(139.0 35.0)')
);
```
【Typescript】FirebaseのGoogle認証を使用して、ユーザー情報を取得する

```typescript

async login () {
  try {
    const res = await auth.signInWithPopup(provider)

    //  Property 'email' does not exist on type 'Object'.
    const email = res.additionalUserInfo.profile.email
  }
}

```

上記のようにfirebaseで用意されている`signInWithPopup()`を使用して、返り値であるユーザー情報を状態管理ライブラリに持たせようとしたら、型定義エラーが起きてずっとハマっていました。

### 解決法

auth.currentUserで現在ログイン中のユーザー情報を取得できる

```typescript

async login () {
  try {
    await auth.signInWithPopup(provider)

    this.email = auth.currentUser?.email
    this.name = auth.currentUser?.displayName
  } catch (e) {
    throw new Error('ログインに失敗 ')
  }
}
```
残プロ　第-8回 ~pythonで第N曜日を計算する~

# このプログラムではこんなことします

- datetimeモジュール，calendarモジュールを使用
- 第N曜日を文字列で受け取り，日にちに変換
- 既に過ぎていた場合は，翌月第N何曜日を計算

# サンプル.py


元の文字列は"EveryDay"や"FirstMonday,EverySunday"などです．これを第-7回の関数separateStrで分割し入力しています．

~~~sample.py
import datetime
import calendar

def str2date(str_list):
    date_list = []
    for s in str_list:
        frequency = s[0]
        weekday = s[1]
        delta = weekday_list.index(weekday) - today.weekday()
        if frequency == "Every":
            if weekday == "Day":
                date = today
            else:
                if delta < 0:
                    delta += 7
                date = today + datetime.timedelta(days=delta)
        else:
            nth = frequency_list.index(frequency) + 1
            weekday_first, _ = calendar.monthrange(year=today.year, month=today.month)
            day = 7 * (nth-1) + (weekday_list.index(weekday) - weekday_first) % 7 + 1
            if day >= today.day:
               delta = day - today.day
               date = today + datetime.timedelta(days=delta)
            else:
                weekday_first, _ = calendar.monthrange(year=today.year, month=today.month+1)
                day = 7 * (nth-1) + (weekday_list.index(weekday) - weekday_first) % 7 + 1
                date = datetime.date(year=today.year, month=today.month+1, day=1) + datetime.timedelta(days=day-1)
        date_list.append(date)
    return date_list


frequency_list = ['First', 'Second', 'Third', 'Fourth']
weekday_list = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday']
today = datetime.date.today()
~~~


第N曜日の計算には[nkmkさんのサイト](https://note.nkmk.me/python-calendar-day-of-nth-dow/)を参考にさせていただきました．
Java勉強_Java初心者問題を解く

次のプログラムを完成しなさい。

>(1)クラス名:Salary
>>① フィールド :
>>>String name
>>>int salary (年俸)

>>② 作成者:
>>>Salary(Stringn, ints)を受けてname, salaryに代入

>>③メソッド:
>>>getInfomation1()メソッドで名前と年俸を出力

>(2)クラス名:Test34 ==> Salaryを継承する
>>①フィールド :
>>>String department（部署）

>>② 作成者:
>>>name、salary、departmentを相続してフィールドに大学入試が必要な場合、親生成者を呼び出すこともできる。

>>③メソッド:
>>>getInfomation2()メソッドで部署出力

>(3) main() 関数で Test34 ob = new Test34 ("野鉄大将"、85000000, "鉄器部屋"); で始まる
>(4)出力
>>名前:夜鉄大将
>>年俸:85000000
>>部署:鉄器店

```java
package firstStep;

public class Question34 {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Test34 ob = new Test34("野鉄大将", 85000000, "鉄器部屋");
		ob.getInformation();
		ob.getInformationV2();
	}
}

class Salary {
	String name;
	int salary;
	
	public Salary(String name, int salary) {
		this.name = name;
		this.salary = salary;
	}
	
	public void getInformation() {
		System.out.printf("名前: %s", this.name);
		System.out.printf("\n年俸: %s", this.salary);
	}
}

class Test34 extends Salary {
	
	String department;
	
	public Test34(String name, int salary, String department) {
		super(name, salary);
		this.name = name;
		this.salary = salary;
		this.department = department;
	}
	
	public void getInformationV2() {
		System.out.printf("\n部署: %s", this.department);
	}
}
```
プロパティについてのまとめ（備忘録）

#プロパティについてのまとめ

###・プロパティ　: 型に紐づいた値のこと

・プロパティの分類
①var,let
②ストアドプロパティ,コンピューテッドプロパティ
③インスタンスプロパティ,スタティックプロパティ,クラスプロパティ

###①var,let
var :　再代入可
let :　再代入不可

###②ストアドプロパティ,コンピューテッドプロパティ
・ストアドプロパティ（値を保持するプロパティ。プロパティオブザーバをもつ。） 

```swift
struct Bird {
    var status = "卵" {
        willSet {
            print("私は\(status)です。次は\(newValue)になります。")
        }
        didSet {
            print("私は\(status)になりました。前は\(oldValue)です。")
        }
    }
    
    func greet() {
        print("私は\(status)です。")
    }
}

var bird = Bird()
bird.greet() //私は卵です。

bird.status = "鳥"
bird.greet()　// 私は卵です。次は鳥になります。私は鳥になりました。前は卵です。私は鳥です。
```
・コンピューテッドプロパティ（値を保持せずに算出するプロパティ）

```swift
struct Human {
    var gender = "男"
    var name : String {
        get {
            if gender == "男" {
                return "太郎"
            } else {
                return "花子"
            }
        }
        
        set {
            if newValue == "太郎" {
                gender = "男"
            } else {
                gender = "女"
            }
        }
    }
    
    func person() {
        print("私は\(name)です。性別は\(gender)です。")
    }
}

var human = Human()
human.person()　// 私は太郎です。性別は男です。
human.gender = "女"
human.person() //　私は花子です。性別は女です。
```

###③インスタンスプロパティ,スタティックプロパティ,クラスプロパティ
①インスタンスプロパティ（型のインスタンスに紐づくプロパティ）

```swift
struct Human {
    var gender = "男"
}

var human = Human()
print(human.name)　//山田太郎

```

②スタティックプロパティ・クラスプロパティ（型そのものに紐づく）

・スタティックプロパティについて

```swift
 struct Animal1 {

//スタティックプロパティはストアドプロパティ・コンピューテッドプロパティとして利用できる。オーバーライドはできない。

        static var weight : Int {
            return 40
        }
        
        static var height: Int = 180
    }
    
    print(Animal1.weight) // 40
    print(Animal1.height) // 180



```

・クラスプロパティについて

```swift
//クラスプロパティはコンピューテッドプロパティとして利用しなければならない。オーバーライド可能。
class Animal2 {
    class var name : String {
        return "Dog"
    }
}

class Animal3: Animal2 {
    override class var name: String {
        return "Cat"
    }
}


print(Animal2.name) //Dog
print(Animal3.name) //Cat
```

#参考
・Swift実践入門
Windows + Visual Studio 2019 で EDK2 の OVMF をビルドする【1.ビルド環境の準備】(2/2)

#【目標】
『Windows 10 に EDK2環境 を構築し、Visual Studio Community 2019 を
　使って OVMF(OvmfPkg) をビルドする。』

#【前回まで】
ビルドに必要なツール類のインストールと設定の途中でした。
今回は残りのツール類のインストールと設定をします。
今回でビルド環境の準備は終了となります。

#【今回の目標】
ビルド環境に必要なツール類のインストールと設定をする(2回目)

#【ツール類のインストール(2/2)】
ツール類のインストール方法について、デフォルト設定から
変更した箇所などを説明します。
なお、インストール順は以下の通りです。
　(1) VS Community 2019
　(2) Python 3.9.5
　(3) NASM 2.15.05
　<B>～ 今回はここから ～
　(4) ASL 20210331
　(5) Visual Studio Code
　(6) Git 2.31.1
　～ ここまで ～</B>

(4) ASL 20210331 の準備
・<B>ASL にはインストーラがありません</B>
　ダウンロードサイトにある iasl-win-20190509.zip を
　ダウンロードして展開します
・<B>展開先は C:\ASL となるようにしてください</B>
　C:\ASL\iasl.exe があれば展開は成功です
　https://github.com/tianocore/tianocore.github.io/wiki/Asl-Setup
・念のため <B>環境変数Path に C:\ASL を追加</B>します
　設定する手順は以下のとおりです
　1) システムのプロパティを開いて、詳細設定タブ にある 
　　 [環境変数(N)] をクリックします
　2) システム環境変数 の Path で [編集(I)] をクリックします
　3) 環境変数名で [新規(N)] をクリックします
　4) C:\ASL を追加します
　5) 環境変数名で [OK] をクリックします
　6) 環境で [OK] をクリックします
　7) システムのプロパティで [OK] をクリックします

(5) Visual Studio Code のインストール
・Visual Studio Code は EDK2のビルド環境としては必要ないのですが、
　次の Git のインストールの際にエディターとして選択可能でしたので
　インストールします
・このインストールでは特別な設定が必要ありませんでしたので、
　画像などは省略します

(6) Git 2.31.1 のインストール
・<B>64bit版のインストーラーを使ってインストール</B>します
・「Choosing the default editor used by Git」では
　<B>「Use Visual Studio Code as Git default editor」を選択</B>します
　![Git画像1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1491958/fa38fa62-100b-50e5-0cab-1240e10bbecf.png)
その他の項目はお好みで設定してください


ビルド環境の準備はここまでです。次回「2.EDK2環境の準備」に続きます。
ありがとうございました。
Sublime Text 4 にしたら Goto Definition(F12) でライブラリの定義に飛べなくなった場合

ちょっと戸惑ったので備忘録。

Sublime Text はデフォルトでプロジェクトの全てのファイルをインデクシングしてくれていて、ライブラリのメソッド（`vendor/` 以下とか）であってもすぐに定義に飛べて便利でしたが、4 にバージョンアップしたところそれが出てこなくなってしまいました。
どうやら 4 からは file indexing はデフォルトで `.gitignore` の指定に従うようになったようです。

この場合 `⌘+,`　から設定ファイルを開き `index_exclude_gitignore: false` にすることで以前のように全てのファイルをインデクシングすることが出来るようになります。また、`folder_exclude_patterns` で除外ディレクトリも指定可能なので合わせて設定しておくことで以前よりノイズを減らすことも可能です。

```json:Preferences.sublime-settings
{
  "index_exclude_gitignore": false,
  "folder_exclude_patterns": [".svn", ".git", ".hg", "CVS", ".Trash", ".Trash-*", "node_modules"],
}
```
bitnami redmine4.＊環境にプラグイン（redmine_bootstrap_kit）をインストールする。

##■プラグインのインストール
　bitnami redmine4.＊系の環境に、古めのプラグイン（redmine_bootstrap_kit）をインストールします。
　windwos版のみ検証し、その他環境は確認しておりませんが他の方の参考になるかもしれないので公開します。
　※インストール作業は割愛しております。
　※プラグインインストール後の動作確認はしておりません、インストール作業のみです。

##■環境：
　`bitnami-redmine-4.1.1-3-windows-x64-installer.exe`
　`redmica1.2.2`
　`Windows10 Home 64bit x64`
　`インターネット接続環境`
　`プラグイン`
　　`Redmine Bootstrap Kit plugin`
　　`This is a Bootstrap Kit plugin for Redmine`
　　`Nicolas Rodriguez 0.2-devel`

##■プラグインの入手
　　以下より入手する。
　　`https://github.com/jbox-web/redmine_bootstrap_kit`

##■インストール（初回）
　プラグインを下記にインストールする。
　１．pluginsディレクトリに、プラグインをコピーする。
　　例）`C:\Bitnami\redmine-4.1.1-3\apps\redmine\htdocs\plugins\redmine_bootstrap_kit`
　　　※プラグインのディレクトリ名はredmine_bootstrap_kitにしておかないとインストールできない　
　２．以下コマンドでインストール
　　　`bundle install`
　　　`bundle exec rake redmine:plugins RAILS_ENV=production`　　
　３．Bitnami Redmine Stack Manager Toolを起動して、以下のサービスを再起動するも停止してしまう。
　　　`redmineThin1、redmineThin2`
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651745/24a6108f-0984-0d80-7f3c-21fe7c8608db.png)
　
　４．エラーログ解析
　　htdocs配下のログファイル（production.log）を確認しても手掛かりなし。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651745/fdbe1120-5af5-3151-328d-ea94dde65524.png)


##■原因解析

　１．コマンドプロンプト（`use_redmine.bat`）を起動して以下のコマンドを動作させる。
　　　`bundle exec thin start -e production`
　２．エラー画面を確認する。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651745/b78b40f9-5d3d-eccb-db48-453380746341.png)
　
　３．以下のエラーに注目して解決方法を検討する。
`4: from C:/Bitnami/redmine-4.1.1-3/apps/redmine/htdocs/plugins/redmine_bootstrap_kit/app/helpers/code_mirror/colorizer_helper.rb:1:in `<top (required)>'`

##■結果
　１．調査していたら以下サイトより、Gemfileファイルに下記gemを追加したら動作すると記載があったので、試してみる。
　　　`gem 'coderay', '1.1.3'  ` 
　　　https://github.com/jbox-web/redmine_bootstrap_kit/issues/12

　２．`Gemfile`を修正して、再度インストールして再起動
　　　※インストール（初回）の２，３と実施する。

　３．インストールが正常にできた

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651745/56a9f3f7-4dfd-75fb-a29d-6179f505cd61.png)

以上です、お疲れ様でした。
TabViewで最後の１つが真ん中あたりで止まっちゃいました


```swift
TabView(selection: $selection,
            content: {
                    Image("1")
                        .resizable()
                        .scaledToFill()
                        .tag(1)
                    Image("2")
                        .resizable()
                        .scaledToFill()
                        .tag(2)
                    Image("3")
                        .resizable()
                        .scaledToFill()
                        .tag(3)
             }
).tabViewStyle(PageTabViewStyle())
```

ってやったら、２枚目と３枚目の間？で遷移が止まってしまいました・・・
.scaledToFillを外したら上手く行きました。
JavaScriptでsetIntervalを学んでみた


＜前提＞
・使用PC；MacBook Air M1(購入日：2021年4月)
・テキストエディタ：VScode

ーーーーーーーーーーーーーーーーーーーーーーーー
こんにちは！シュートです。今日が初投稿となります。

最近、JavaScriptの勉強をスタートしたんですが、HTML/CSSから急に難しくなって、すごく困っていました。

やっと自分の言葉で説明できるようになったので、ここに記録していきたいと思います。

今日のテーマは、setInterval（一定時間ごとに、特定の処理が繰り返される）。


画像のように、”0〜5の数字を1秒づつ出力させる” などですね。

![quita.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1625911/735e43a9-74bc-fbc0-9f29-ab764ec2d7e7.jpeg)


まずは簡単なコードから書いてみよう。

というわけで、下記のコードで実現してみました。


```javascript:qiita.js
let count = 0;
const countUp = function () {
    console.log(count++);
}

const intervalId = setInterval(() => {
    countUp();
    if (count > 5) {       
        clearInterval(intervalId);
    }
}, 1000);
```


英語がたくさん並んで（当たり前やろ）何書いてるか急にわかんない！！
式が長いと、頭パンクしそうになりませんか？笑
（この程度で長いとか言うな）

たったこれだけなのに、コードの意味を理解して、人に説明できるまで2時間もかかってしまいました。笑


ーーーーーーーーーーーーーーーーー

①まず、変数を定義します

```javascript:qiita.js
let count = 0;
```


・0~Xまで数字が変わるので、変数を定義するletを使います。

---------------------------------

②次に、0〜Xまで表示する関数を作ります。

```javascript:qiita.js
const countUp = function () {
    console.log(count++);
}
```

・“count++” で、1ずつ順番に出力されます。
・これで、countUpの中身ができました。

-------------------------------------
③インターバルの機能内容を決めていきます。
まず、それを表す定数を決めます。

```javascript:qiita.js
const = intervalId 
```

--------------------------------------
④定数に代入する関数を作ります。

```javascript:qiita.js
setInterval( 関数, 時間間隔(ミリ秒));
```

関数より先に、時間間隔だけ決めます。

```javascript:qiita.js
setInterval( 関数, 1000);  // 1000ミリ秒=1秒 
```

これで、1秒間隔と決まりました。

---------------------------------------
⑤関数を作る。

```javascript:qiita.js
 setInterval( () => {
    countUp();
}
```

これだけだと、
このインターバル表示が止まりません。

永続的に数字が出力され続けます。

なので、出力を止める条件が必要です。
それが、次のif文です。

---------------------------------------
⑥if文を作る。

```javascript:qiita.js
 if (count > 5) {      
        clearInterval(intervalId);
    }
```

・5以上になったら、出力を止める。
・出力を止めるのが、 clearInterval（インターバルをクリアする）。
・（）の中は引数が入る。止めたい関数名を書く。ここでは、intervalId。

-------------------------------------
⑦　④〜⑥をまとめると、こう。

```javascript:qiita.js
const intervalId = setInterval(() => {
    countUp();
    if (count > 5) {      
        clearInterval(intervalId);
    }
}, 1000);
```

------------------------------------
以上です。

最後までご一読いただき、ありがとうございました！

言葉のチョイスがわかりにくかったら、ぜひコメントをお願いいたします！
（そこは関数名やなくて変数名やろがい！とか笑）

シュート
ちょ、待てよ、、ちゃんとUbuntuじゃん


#はじめに
前回、[ちょ、待てよ、、営業でも簡単にインスタンス立つじゃん](https://qiita.com/chomateyo/items/f319c54faaf9ffcd4036)にてGCP上に初めてインスタンスを作成。
興奮と感動が冷めやまない夜を過ごしたのであった。
##インスタンスの中身（Ubuntu）ってどうなってるか見てみた（見ないで//）
GCP環境にてUbuntuイメージを選択した最小インスタンスを構築する。
作成後、緑のマークとともにインスタンスの正常性を肉眼で検知。
だが裸を見たことのないのになぜ中身がUbuntuでかつインスタンスが正常だと言えるのか！？
環境を初めて作ったとある営業マンは思う。
ちょ、待てよ、、本当にUbuntuが動いているのか確認しないと。

まずはGCP環境にアクセス。
![スクリーンショット 2021-06-08 19.29.15.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/9cf83a9d-8062-878f-61c6-4324e7a9d32b.png)

今日も緑のマークであることを確認。
「接続」のSSH横をクリックし、インスタンスにアクセスを試みる。
なにやら複数選択肢があるが、ここは「ブラウザウィンドウで開く」を選択。
![スクリーンショット 2021-06-08 19.30.26.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/1c1e31b9-5f17-d81f-a99a-3e3712051531.png)

お、アクセス開始のゴングが鳴ったようだ。
![スクリーンショット 2021-06-08 19.31.29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/8da3e650-0dd5-b883-9be1-91e20ee94cd1.png)

ちょ、、待てよ、、これがインスタンスの中身！？
絶景だ。
![スクリーンショット 2021-06-08 19.32.47.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/faf82e0c-7b0f-abbd-a85f-108e4b813f97.png)

よしLPICの教科書を見ながらコマンド入力だ！
まずは「home」ディレクトリへ移動。
![スクリーンショット 2021-06-08 22.40.28.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/b44f17ed-fc54-aa62-a81b-98fb1b8e6a05.png)

homeディレクトリ配下に移動後は状況確認！
必殺`ls`
![スクリーンショット 2021-06-08 22.41.53.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/a3648d19-1ed7-7738-d17c-068d132e0b4b.png)

ぬおおおお。
Ubuntuの文字を発見！
ちゃんとイメージが入っているんなだな。
次はUbuntuのバージョン確認をしてみる。
`cat /etc/issue`
![スクリーンショット 2021-06-08 22.44.55.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/b85e9cc1-acab-6a2c-d2ec-c625e65173ae.png)

バージョンは「Ubuntu 16.04.7 LTS」であることを確認。
よし本当にインスタンスの中身はUbuntuであり、バージョンも確認できた。
他にどんなパッケージが入っているのかもついでに見てみる。
![スクリーンショット 2021-06-08 22.47.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/f2d14704-0f79-2683-4229-691b63e5b558.png)

おお、、パンドラの箱を開けてしまったようだ。
よくわからないけどたくさん入っている。
こちらの内容を今度にしよう。
では確認もできたので、ここらで
`exit`
![スクリーンショット 2021-06-08 22.50.21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578917/6705613a-a95a-ee30-b0d1-abd607d91442.png)

#次回
流行り（？）のDockerを入れてみた
更新中のため未定

６月１２日現在　更新中（完成はまだ先）

#ルーブックキューブをモーターでそろえる

ただただ　自分メモ代わりに
　ちょっと　でも誰かのためになったり
いや、やっぱり　自分がやったこと　忘れても　なんとなく　理解できるよう

#環境
+ python3.9.1
+ Opencv 4.5.1
+ Arduino uno
+ デイジーチェーン
+ Visual Studio Code
+ Windows10
+ ３Dプリンター(Adventure3, 材料PLA)

#使用道具

[秋月ステッパーモータ](https://akizukidenshi.com/catalog/g/gP-05372/)
(バイポーラ　ステッピングモーター　ＳＭ－４２ＢＹＧ０１１)

[秋月L6470モータドライバー](https://akizukidenshi.com/catalog/g/gK-07024/)
(Ｌ６４７０使用　ステッピングモータードライブキット)

[カップリング](https://www.amazon.co.jp/%E3%83%97%E3%83%AC%E3%83%9F%E3%82%A2%E3%83%A0%E3%83%93%E3%83%BC%E3%83%A0%E3%82%AB%E3%83%83%E3%83%97%E3%83%AA%E3%83%B3%E3%82%B0-%E3%83%A2%E3%83%BC%E3%82%BF%E3%83%BC%E3%80%81%E3%82%B7%E3%83%A3%E3%83%95%E3%83%88%E3%82%AB%E3%83%97%E3%83%A9%E3%83%BC-%E3%82%A2%E3%83%AB%E3%83%9F%E3%83%8B%E3%82%A6%E3%83%A0%E5%90%88%E9%87%91-%E3%80%815mm%E3%81%8B%E3%82%898mm%E3%83%A2%E3%83%BC%E3%82%BF%E3%83%BC%E8%BB%B8%E7%B6%99%E6%89%8B%E3%80%812%E5%80%8B-2mm%E3%82%A2%E3%83%AC%E3%83%B3%E3%83%AC%E3%83%B3%E3%83%81/dp/B08H136GN4/ref=sr_1_56?__mk_ja_JP=%E3%82%AB%E3%82%BF%E3%82%AB%E3%83%8A&dchild=1&keywords=%E3%82%AB%E3%83%83%E3%83%97%E3%83%AA%E3%83%B3%E3%82%B0&qid=1623156617&sr=8-56)
ルービックキューブをモーターをつなぐ　ジョイント

[直流安定化電源](https://www.amazon.co.jp/Wanptek-%E5%8F%AF%E5%A4%89%E7%9B%B4%E6%B5%81%E5%AE%89%E5%AE%9A%E5%8C%96%E9%9B%BB%E6%BA%90%E8%A3%85%E7%BD%AE-%E5%B0%8F%E5%9E%8B%E5%AE%89%E5%AE%9A%E5%8C%96%E7%9B%B4%E6%B5%81%E9%9B%BB%E6%BA%90-%E3%82%B9%E3%82%A4%E3%83%83%E3%83%81%E3%83%B3%E3%82%B0%E9%9B%BB%E6%BA%90-%E3%80%81%E5%AE%89%E5%AE%9A%E3%81%97%E3%81%9F%E5%87%BA%E5%8A%9B%E3%80%814%E6%A1%81%E3%81%AE%E3%83%87%E3%82%B8%E3%82%BF%E3%83%AB%E3%83%87%E3%82%A3%E3%82%B9%E3%83%97%E3%83%AC%E3%82%A400-01V/dp/B08B5SJCJ6/ref=sr_1_24?__mk_ja_JP=%E3%82%AB%E3%82%BF%E3%82%AB%E3%83%8A&dchild=1&keywords=%E5%AE%89%E5%AE%9A%E5%8C%96%E9%9B%BB%E6%BA%90&qid=1623157641&sr=8-24)
30V-10A

[Arduino uno](https://akizukidenshi.com/catalog/g/gM-15574/)
Arduino uno 互換マイコンボード



###お世話になった　サイト
[L6470とモータのつなぎ方](https://kogakubu.com/?p=2918)
工学部生の生プレスさん
arduino、ステッパーモータ、L6470モータドライバのつなぎかたなど

[arduinoプログラム](http://spinelify.blog.fc2.com/blog-entry-81.html)
北の国から電子工作（仮）さん

[3Dプリンター](https://www.thingiverse.com/thing:2999309)
キューブをまわすボディ

[キューブ回転記号](https://cubenavi.com/notations/notations-basic/)

キューブの色を取得コード（忘れた、申し訳ない)


###Python,Opencvで画像処理
カメラはスマートフォン（galaxy s9)
カメラアプリ　　[iriuncam](https://iriun.com/)


#記事一覧

[NO.1カメラ起動＋BGR取得](https://qiita.com/otoboke162/items/e5eebb6d1fdf4fdcf9cd)
python opencv ウェブカメラで　リアルタイムで色（BGR)を取得

[No.2取得したBGRを画面左上に表示](https://qiita.com/otoboke162/items/4a4aa661f47f5a1a13b2)
タイトルそのまま
【Rails】Your Yarn packages are out of date!   Please run `yarn install --check-files` to update.と怒られた

## はじめに
Railsでの環境構築中に起きたエラーを備忘録として残します。

## 解決方法

サーバーを立ち上げると`yarnがインストールされていないです`のような以下のエラーが発生

```:ターミナル 
$ rails s

=> Booting Puma
=> Rails 6.0.3.2 application starting in development
=> Run `rails server --help` for more startup options
error Couldn't find an integrity file
error Found 1 errors.


========================================
  Your Yarn packages are out of date!
  Please run `yarn install --check-files` to update.
========================================


To disable this check, please change `check_yarn_integrity`
to `false` in your webpacker config file (config/webpacker.yml).


yarn check v1.22.4
info Visit https://yarnpkg.com/en/docs/cli/check for documentation about this command.


Exiting
```

あれ？インストールしているはずだけど！と思いながら
エラー通りにひとまず以下のコマンドを実行

```:ターミナル 
$ yarn install --check-files
```

しかし、解決できず。。。

そこで以下のコマンドで、yarnのインストールではなく
アップグレードしてあげることで解消することができました！

```:ターミナル 
$ yarn upgrade
```

同じ境遇の方はぜひ試してみてください。
ターミナル　よく使う基本コマンド集


よく使うんだけど、ど忘れしちゃう。
そんなコマンドをまとめました。個人的に当たり前なものは省略！

#現在のディレクトリのファイルを表示
```
$ ls [ディレクトリ名]

#オプション
ls -a      *先頭にピリオドがあるファイルも表示する。　ex).env など
ls -l      *詳細確認できる。　　　　　　　　　　　ex)パーミッション確認・オーナー名など
ls -1      *リストを縦に並べる。見やすい！　数字の１です
ls --help  *オプションの紹介してくれる！
```

#ディレクトリの作成・削除
rm -rfは取り返しつかないミスになり得るので注意。。

```
mkdir    *作成
rm -r   [ディレクトリ名]   *ディレクトリとその中身を削除する
rm -rf　[ディレクトリ名]  　*ディレクトリとその中身を警告なしで削除する
rm -f 　[ファイル名]   　 *ファイルを警告なしで削除する
```

#ファイルを表示
```
$ cat [ファイル名] 　　　*ファイルの閲覧ができます。

#オプション
cat -n 　　　　　　    *行番号つけて表示。　Numberですね。
cat fileA > fileB    *Aの内容をBに上書き記載。
cat fileA >> fileB   *上書きではなく追加。
less [ファイル名]       *１画面にまとめて表示。
```

#ファイル名の変更・移動
```
mv 変更するファイル名   変更したいファイル名　
mv 移動したいファイル名　移動後のディレクトリ
```

#ファイルのコピー
```
cp hoge.html etc/       *hoge.htmlを相対パスでetc/というディレクトリの中にコピーする
cp hoge.html hoge2.html  *hoge.htmlをhoge2.htmlという名前でコピーする
cp −r dir /etc/  #dirというディレクトリとその中身を絶対パスで/etc/にそっくりコピーする
```

#grep

```
grep オプション 検索文字列 ディレクトリ名   
 
#オプション
grep -r  #指定したディレクトリ以下をたどって検索する
grep -i  #大文字小文字を区別せずに検索する
grep -l  #検索した文字列が含まれているファイル名のみを表示する
grep -n  #検索した文字列が書いてある行番号を表示する。-lオプションと併用することはできない
grep -e  #複数の検索条件を指定する
grep -v  #パターンに一致しない行を表示する
```


#プロセス表示

```
ps aux  #起動しているすべてのプロセスを表示する
ps aux | grep hoge  #上記のgrepコマンドと組み合わせて、psコマンドで検索したプロセスでhogeという文字が含まれるプロセスだけを表示する
ps aux | grep hoge | grep -v grep  #上記のコマンドで、grepコマンド以外のプロセスでhogeが含まれるプロセスだけを表示する
```



今後使うものは再度追加していく！
AccessVBA　ユーザーインターフェース周り小ネタ

#### 1. 定型入力エラー時のエラーダイアログを置き換える

定型入力エラー時、Access標準の不親切な？ダイアログが表示されるので、これをもっと親切なものに置き換える。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/170624/b1ab0544-2f20-90b3-1f02-50b8808f2277.png)

①FormのErrorイベントで、エラーが発生した項目名＆エラーNoを特定。
　今回の場合、エラーNo.2279：「アプリケーション定義またはオブジェクト定義のエラーです」

②新しく定義しなおしたエラーメッセージを表示

③Errorイベントの引数Responceに処理継続（acDataErrorContinue）、DataErrにエラーなし（0）を設定。
　RunCommandでアンドゥを実行。
　エラーの原因となったデータ修正を元に戻す。

```VB
Private Sub Form_Error(DataErr As Integer, Response As Integer)

　　If DataErr = 2279 And _
　　　 Screen.ActiveControl.Name = "機器ID" Then　　　　　　　　　　　　　　　　・・・①
　　　  Msgbox "入力内容のエラーです", vbExclamation + vbOkOnly, "入力エラー"　 ・・・②
　　　　Response = acDataErrContinue　　　　　　　　　　　 　　　　　　　　　　　・・・③
　　　　DataErr = 0
　　　　DoCmd.Runcommand acCmdUndo
　　　　Me![機器ID].SetFocus
　　End If

End Sub
```

***
#### 2. 帳票形式フォームで、カレント行をハイライト表示する

ネットで検索すると、上位に出てくるのは軒並み「条件付き書式」を使った方法。
ただこれだと、画面が非常にちらついて、ときに画面操作にも悪影響を及ぼすことがあって。

で、参考にさせていただいたのはこちら（↓）。
[hatena chips：カレント行の背景色の変更　その3](https://hatenachips.blog.fc2.com/blog-entry-21.html)

非常に参考になりましたが、筆者的にちょっとアレンジしたのは次の２点。
1) 交互に行の色を変える設定に対応するため、データを表示するテキストボックスの背景色は色なしのまま。
　最背後に設定したテキストボックスのフォントの色を、ハイライト表示の色に設定。
2) 最背面に設定したテキストボックスで、コントロールソースに設定している式中の"g"は、フォームの幅に応じて調整。

ちなみに、筆者の職場の環境（Windowos10 Pro/Access2013）でもちらつきは激減し、快適に動いております。

***
#### 3. URLを指定して表示

これまでよくあったんは、さしずめIEをオブジェクト参照するこのパターンかな？

```VB
Private Sub URL表示_Click()

    Dim ret As Integer, objIE0 As Object

    If IsNull(Me![URL]) Then Exit Sub

    Set objIE0 = CreateObject("InternetExplorer.Application")
    objIE0.Visible = True
    objIE0.Navigate Me![URL]

End Sub
```

が、これではいまさらの？IEしか対応でけへんし:frowning2:
いろいろ調べたら、Windows Scripting Hostを使うこんな方法があるらしいです。

```VB
Private Sub URL表示_Click()

   Dim objWSH As Object
    
    Set objWSH = CreateObject("WScript.Shell")
    objWSH.Run Me![URL], 1

End Sub
```

へぇー、これやとIEに限らず、標準のブラウザで指定したURLを開けるようです。

***
#### 4. サブフォームの特定項目にフォーカスを当てる

意外とやる機会ない？かもしれませんが、いったんサブフォームのオブジェクト自体にフォーカスを移して、さらにその中の個別項目をSetFocusします。

```VB
    Me![サブフォーム].SetFocus
    Me![サブフォーム].Form![サンプルサブフォーム]![ID].SetFocus
```
Ubuntu 18.04から20.04に上げたときにMySQLdでハマった

Ubuntu 18.04から20.04に上げたら、MySQL 5.7 -> MySQL 8.0 になった。
そのときにMySQLdが起動できなくなったメモ


## 原因の調査方法

/var/log/mysql/error.log を確認

`systemctl status mysql.service`でエラー確認

## 設定ファイルでのはまり

/etc/mysql/mysql.conf.d/mysqld.cnf

に以下が書いてあったのでコメントアウト。

```diff:
- innodb_file_format = Barracuda
```

これでmysqldが動くようになった。

```
service mysqld.start
```

## 古いMySQL5.7のアンインストールでのハマり

不要になったのでMySQL5.7を消したら、mysql.service まで消されて
MySQLdが起動しなくなった。

```sh
sudo dpkg --purge mysql-server-5.7
```

### 対処

reinstallで解決した。

```sh
sudo apt --reinstall install mysql-server-8.0
```
ベクトルの外積をWolframAlphaとSymPy Liveでやってみた。

(オリジナルポスト)

https://pianofisica.hatenablog.com/entry/2021/04/24/190000#%E3%83%99%E3%82%AF%E3%83%88%E3%83%AB%E3%81%AE%E5%A4%96%E7%A9%8D

#WolframAlphaで

https://www.wolframalpha.com/input/?i=%5B3%2C0%2C0%5D+%5B0%2C5%2C0%5D+%E5%A4%96%E7%A9%8D&lang=ja

結果:
(0, 0, 15)

https://www.wolframalpha.com/input/?i=%5B0%2C5%2C0%5D+%5B3%2C0%2C0%5D++%E5%A4%96%E7%A9%8D&lang=ja

結果:
(0, 0, -15)

https://www.wolframalpha.com/input/?i=%5B%5B3%5D%2C%5B0%5D%2C%5B0%5D%5D+++%5B%5B0%5D%2C%5B5%5D%2C%5B0%5D%5D+%E5%A4%96%E7%A9%8D&lang=ja

https://www.wolframalpha.com/input/?i=+%5B%5B0%5D%2C%5B5%5D%2C%5B0%5D%5D++%5B%5B3%5D%2C%5B0%5D%2C%5B0%5D%5D++%E5%A4%96%E7%A9%8D&lang=ja



https://www.wolframalpha.com/input/?i=%7B3%2C0%2C0%7D+%7B0%2C5%2C0%7D+%E5%A4%96%E7%A9%8D&lang=ja

https://www.wolframalpha.com/input/?i=%7B0%2C5%2C0%7D+%7B3%2C0%2C0%7D++%E5%A4%96%E7%A9%8D&lang=ja



# SymPy Liveで
https://live.sympy.org/

```python
import sympy as sp
def Crs(A, B):
    return sp.expand(sp.Matrix([
            [A[1,0]*B[2,0]-A[2,0]*B[1,0]],
            [A[2,0]*B[0,0]-A[0,0]*B[2,0]],
            [A[0,0]*B[1,0]-A[1,0]*B[0,0]]
                                ]))
print("# ",Crs(sp.Matrix([3,0,0]), sp.Matrix([0,5,0])))
print("# ",Crs(sp.Matrix([0,5,0]), sp.Matrix([3,0,0])))
print("# ",Crs(sp.Matrix([[3],[0],[0]]), sp.Matrix([[0],[5],[0]])))
print("# ",Crs(sp.Matrix([[0],[5],[0]]), sp.Matrix([[3],[0],[0]])))
#  Matrix([[0], [0], [15]])
#  Matrix([[0], [0], [-15]])
#  Matrix([[0], [0], [15]])
#  Matrix([[0], [0], [-15]])
```
BoidsアルゴリズムのUnityリンク集 


# 日本語

https://shitakami.hatenablog.com/entry/2020/08/30/230322

https://drive.google.com/file/d/1wuCYUSEL4A3HVGlvB5efee6WWT5-Yfuo/view


https://www.isus.jp/wp-content/uploads/pdf/755_fish-flocking-with-unitysimulating-behavior-of-object-moving-with-ai.pdf


# 英語

https://zklinger.com/unity-boids/

Sample Project

https://unitylist.com/p/i7f/boids

# 中国語

https://www.cnblogs.com/SouthBegonia/p/10975851.html
Next.jsとNuxt.jsのサーバサイドレンダリング、用語の違いを表にまとめてみた

## はじめに

こんにちわ、dtakkiyです!

私は、フロントエンドの開発をvue.jsをベースとするNuxt.jsからはじめました。
そして現在、React.jsをベーズとするNext.jsの開発を学んでいるのですが、
Next.jsのドキュメントを読み進めるにあたって、どうしてもNuxt.jsと比較し技術を理解しようする自分がいました。
ただプロダクトが異なるので当然のことなのですが、似ている概念があるにも関わらず、両者で使われる言葉はかなり違っています。

そこで今回は、私がドキュメントを読み進めるにあたって、特に理解が難しかったサーバサイドレンダリングに絞り、Next.jsとNuxt.jsで使用している言葉を比較表としてまとめてみました。
また`SPA`などの誤解しやすい関連用語の解説もいれてみました。

なお比較表で使用した単語は、各々の公式ドキュメントの表記を利用しています。

### 公式ドキュメント

- [next.js](https://nextjs.org/docs/getting-started)
- [nuxt.js](https://nuxtjs.org/docs/2.x/get-started/installation) 

### 執筆時のバージョン

- next.js: version 10.2
- nuxt.js: version 2.14

## 比較表と関連用語

### 比較表

![ 2021-06-09 20.57.19.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/166484/3af46fa2-178a-b5b0-4981-9bc989579d5a.png)

かなりシンプルにまとまりました。

なおNext.jsではデフォルトで`Static Generation`が選択されるのに対し、Nuxt.jsでは`SSR`が選択されます。

### 関連用語の解説

続いて誤解しやすい関連用語の解説をします。

- rendering(レンダリング): 何らかのデータを元に表示内容を生成すること。

- Pre-rendering(プレレンダリング): 事前にサーバ側でHTMLを生成すること。導入することにより、一般的にクライアント側で表示が高速化する。プレーンなReact.jsやVue.jsではプレレンダリングは行われず、クライアントでのレンダリングとなる。

- SPA: Single page Applicationの略。一般的には、複数ページではなく、単一のページで構成されたwebアプリケーションのことを意味する。代表的なアプリとして、Facebookのメッセンジャーなどがある。

- PWA: Progressive Web Appsの略。Webアプリでありながら、ネイティブアプリと同じ様に動作するアプリケーションのこと。プッシュ通知やオフラインでの動作など、ネイティブアプリ特有の機能を利用できる。


## おわりに

いかがだったでしょうか？
読者の方のサーバサイドレンダリングの技術理解の一助になれば幸いです。
AWS Athena で配列の要素を Column にする

一回 `unnest` にした結果を集計してカラムに戻してやることで実現した。

```sql
WITH dataset AS (
	SELECT ARRAY [1,2,3] AS items
)
SELECT MAX(CASE WHEN i = 1 THEN i END) AS one
	 , MAX(CASE WHEN i = 2 THEN i END) AS two
	 , MAX(CASE WHEN i = 3 THEN i END) AS three
FROM dataset
	     CROSS JOIN UNNEST(items) AS t(i)
```

こんな感じの結果になるよ。

![スクリーンショット 2021-06-09 21.16.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/142263/c03899c8-1d27-cbbf-dfdc-ca0d40d04b33.png)

もっといい方法があったら教えて下さい。
IPsec とは

## 勉強前イメージ

よく聞くけど、あんまりわかってない・・・

## 調査

### IPsec とは

Security Architecture for IPの略で、暗号化通信を行うためのプロトコルを組み合わせた技術で、
VPNの通信プロトコルなどで使用されています。
IPsecはネットワーク層で動作します。

### IPsecで使用される方式

IPsecには接続方式が以下の2種類あります。

- トランスポートモード

IPアドレスを付け加えるのではなく、もとのIPパケットにセキュリティプロトコルを追加します。
IPヘッダを変更せず、もとのIPヘッダで転送されます。
第4層以上のデータ部のみ暗号化されます。

以下がトランスポートモードのヘッダになります。
IPヘッダが変更されないので、セキュリティプロトコルのAHヘッダのみが追加されています。

![1# IPsec とは - diagrams.net - Google Chrome 2021-06-.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/129517/3f71d569-6f4c-9271-0591-f970b5af9191.png)


- トンネルモード

元々のIPパケットに新しいIPアドレスとセキュリティプロトコルを追加します。
IPヘッダを暗号化され、追加されたIPヘッダでパケットが転送されます。
第4層のデータ部も暗号化されます。

以下がトンネルモードのヘッダになります。
追加されたIPヘッダとセキュリティプロトコルが追加されています。

![2# IPsec とは - diagrams.net - Google Chrome 2021-06-.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/129517/cbac7e8c-81af-2015-e89d-6abe02130ac3.png)


### IPsecで使用されるプロトコル

IPsecは以下の3つのプロトコルで構成されています。

- AH

Authentication Header の略で、 `認証` を行うプロトコルです。
認証情報をパケットに追加して送信、
受信側はAHの情報を確認して問題なければIPパケットを取り出して確認します。

- ESP

Encapsulated Security Payload の略で、 `暗号化` を行うプロトコルです。
暗号化にはDESや3DESやAESなどがあります。

- IKE

Internet Key Exchange protocol の略で、 `鍵交換` を行うプロトコルです。
 

## 勉強後イメージ

IPsecがプロトコルじゃなくて、プロトコルの組み合わせなのか。

## 参考

- [IPsecをはじめから](https://www.infraexpert.com/study/study10.html)
- [意外と知らない？ITトレンド用語](https://www.ntt.com/bizon/glossary/e-i/ipsec.html)
- [IPsecの仕組みとSA、AH、ESP、IKEの関係を理解してみよう！](https://itmanabi.com/ipsec/)
CarrierWaveをrailsアプリに導入する方法

#CarrierWaveとは??
CarrierWaveは、画像をアップロードできるgemの一つです。
非常に簡単に扱えるので、初学者の方でも躓かずに導入することができると思います。
この記事はrailsプロジェクトが作成してあることを前提に書いています。
#前提
・開発環境：cloud9
・OS:ubuntu
・railsのバージョン:5.2.5

#CarrierWaveをインストール
まずgemファイルに以下のようにコードを記入します。

```:Gemfile
gem 'carrierwave', '~> 2.0'
```
そして、バンドルインストールします。

```
$ bundle install
```
これでCarrierWaveのインストールは完了です!
#アップローダークラスの作成
以下のコードでアップローダークラスを作成します。

```
$ rails g uploader (アップローダー名)
```
アップローダー名は任意です。自分は「アップローダー名＝image」としました。

```
$ rails g uploader image
```
すると、app/uploaders/image_uploader.rbが生成されます。
このファイルについて簡単に説明します。

rmagickというgemをインストールし、画像アップロードの設定に関するコードを記入すると、
色々な機能をつけることができたりします。
ただし、この記事では触れませんが、以下の参考記事ではCarrierWaveとrmagickの導入から使い方まで
書かれていますので参考にしてみてください。

参考：[【Rails】CarrierWaveとrmagickで画像アップロード機能を作る](https://pg-happy.jp/carrierwave-rmagic-uploader.html)

#アップロードする画像のカラムを追加
アップロードする画像を保存するためのカラムを作成していない場合は、以下のようにカラムを追加してください。
以下はユーザーのプロフィール画像をアップロードできるようにするため、usersテーブルにimageカラムを追加しています。

```
$ rails g migration add_image_to_users image:string
```

```
$ rails migrate:db
```
画像を保存するためのカラムimageは、なんで文字列（string)なの??と疑問に思うかもしれません。
じつは、imageカラムはアップロードした画像のファイル名を保存するためのカラムなのです。
データベースに画像データという重いデータを保存していては、データベースサーバを圧迫してしまいますからね。

また、セキュリティ対策として以下のように、取得できるパラメータを制限している場合は、imageカラムにアップロードした画像ファイル名を保存できるようにしましょう。

```:app/controllers/users_controller
  private
  
  def user_params
    params.require(:user).permit(:name, :email, :password, :password_confirmation, :introduce_comment, :image)
  end
```
#アップローダークラスとimageカラムの結び付け
アップローダークラスとimageカラムを結びつけるためにapp/models/user.rbに以下のコードを追記します。

```
class モデル名 < ActiveRecord
  mount_uploader [:カラム名], [アップローダークラス]
end
```
例えば、imageカラムとImageUploaderクラスを結びつけるには

```
class User < ApplicationRecord
  mount_uploader :image, ImageUploader
end
```
を追記します。
これで完了です。
#画像がアップロードできる編集フォームを作成する。
では、実際に画像をアップロードできるようにフォームの作成

```:edit.html.erb
<%= form_with(model: @user, local: true) do |f| %>
    
  <div class="form">
    <%= f.label :image, '画像' %>
    <%= f.file_field :image, class: 'form-control image-form' %>
  </div>
    
  <div class="form">
    <%= f.label :name, '名前' %>
    <%= f.text_field :name, class: 'form-control' %>
  </div>
      
  <div class="form">
    <%= f.label :introduce_comment, '自己紹介文' %>
    <%= f.text_area :introduce_comment, class: 'introduce-form-control' %>
  </div>
      
  <%= f.submit '更新する', class: 'edit-btn' %>
<% end %>
```
画像のアップロードフォームは__file_field__でファイル選択ボックスを実装することができます。
これで画像をアップロードすることができるようになります。
#アップロードした画像の表示方法

```:show.html.erb
 <% if @user.image? %> 
    <p>
      <%= image_tag @user.image.url %>
    </p>
  <% end %>
```
このようにimage_tagで画像を表示します。また、__urlメソッド__により画像データの保存場所のpathを取得しています。

#アップロードした画像の保存場所
実際の画像データの保存場所はpublic/uploads/user/画像ファイル名に保存されます。
画像をアップロードしたら、確認してみましょう。
#最後に
CarrierWaveの実装方法については、多くの記事が出ていますので
プログラミング初学者にとっても簡単に実装できました。

[【Rails】 CarrierWaveチュートリアル](https://pikawaka.com/rails/carrierwave)の記事が非常に参考になりましたので
こちらを参照することをお勧めします。
【Swift】アラートのテンプレート

# テンプレート


~~~ swift
struct AlertUtils {
    private static var alertController = UIAlertController()
    
    static func alert(title: String, message: String, view: UIViewController) {
        alertController = UIAlertController(title: title,
                                            message: message,
                                            preferredStyle: .alert)
        alertController.addAction(UIAlertAction(title: "OK",
                                                style: .default,
                                                handler: nil))
        view.present(alertController, animated: true)
    }
}

~~~

# 使用方法

~~~ swift
AlertUtils.alert(title: "タイトル", message: "メッセージ", view: ViewController())
~~~

# 終わりに

コード貼り付けただけですみません。（特に説明することがない・・・）
apt upgradeでエラー吐いた時の対処（備忘録）



``$ sudo apt update``
``$ sudo apt upgrade``

を実行したところ次のようなエラーが出た。

```
$ sudo apt upgrade
Reading package lists... Done
Building dependency tree
Reading state information... Done
Calculating upgrade... Done
Some packages could not be installed. This may mean that you have
requested an impossible situation or if you are using the unstable
distribution that some required packages have not yet been created
or been moved out of Incoming.
The following information may help to resolve the situation:

The following packages have unmet dependencies:
 distro-info-data : Breaks: distro-info (< 0.20~) but 0.18ubuntu0.18.04.1 is to be installed
 dpkg : Breaks: libapt-pkg5.0 (< 1.7~b) but 1.6.13 is to be installed
E: Broken packages
```

とりあえず何がupgradeできなかったのかを見る。

```
$ apt list --upgradable
Listing... Done
ubuntu-advantage-tools/bionic-updates 27.0.2~18.04.1 amd64 [upgradable from: 20.3]
N: There are 2 additional versions. Please use the '-a' switch to see them.
```
どうやらubuntu-advantage-toolsなるものがupgradeに失敗したっぽい。
調べたところ、removeしても問題なさそうなので、

```
$ sudo apt remove ubuntu-advantage-tools
Reading package lists... Done
Building dependency tree
Reading state information... Done
The following packages will be REMOVED:
  ubuntu-advantage-tools ubuntu-minimal
0 upgraded, 0 newly installed, 2 to remove and 0 not upgraded.
After this operation, 275 kB disk space will be freed.
Do you want to continue? [Y/n] y
dpkg: warning: files list file for package 'ubuntu-advantage-tools' missing; assuming package has no files currently installed
(Reading database ... 90724 files and directories currently installed.)
Removing ubuntu-minimal (1.450.2) ...
Removing ubuntu-advantage-tools (20.3) ...
```
再度update

```
$ sudo apt update
Hit:1 http://jp.archive.ubuntu.com/ubuntu bionic InRelease
Get:2 http://jp.archive.ubuntu.com/ubuntu bionic-updates InRelease [88.7 kB]
Hit:3 https://packages.microsoft.com/ubuntu/20.04/prod focal InRelease
Get:4 http://jp.archive.ubuntu.com/ubuntu bionic-backports InRelease [74.6 kB]
Get:5 http://security.ubuntu.com/ubuntu bionic-security InRelease [88.7 kB]
Fetched 252 kB in 2s (123 kB/s)
Reading package lists... Done
Building dependency tree
Reading state information... Done
All packages are up to date.
```
$ flutter doctorで，'Unable to find any JVMs matching version "1.8". 'が出たのでメモ

## はじめに

自分の備忘録として残しておきます．


macにflutterをインストールしてPathの設定を終えたので，`flutter doctor`を実行したところ，下記のエラー．

```bash
Unable to find any JVMs matching version "1.8".
```


環境変数`JAVA_HOME`設定を試したけれど解決せず．


## 解決方法
以下を実行しました．

```
brew install --cask homebrew/cask-versions/adoptopenjdk8
```


HomebrewからAdoptOpenJDKをインストールすることでエラーが解消されました．
pyMOLでGROMACSのトラジェクトリーを読み込む


https://pymolwiki.org/index.php/Load_traj

```bash
# gromacs trajectory, using "mytraj" as object name
load      sampletrajectory.gro, mytraj
load_traj sampletrajectory.xtc, mytraj, state=1
```

mytrajはトラジェクトリーを格納するオブジェクトの名前で無くても良い。

データのロードや描画が重くなるのを防ぐため、あらかじめ不要な分子（溶媒やイオンなど）を削除しておくとよい。
UnityでAssetPackのビルドをビルドパイプラインに組み込む


UnityでPlay Asset Deliveryを使うアプリのビルドを、Googleが提供するビルド方法(Unityエディタの専用メニューからビルド)ではなく、一般的なビルドパイプラインから呼び出す方法をまとめました。
これで BuildSettingsウィンドウのビルドや、Unity Cloud Buildによるビルドでも、AppBundleにAssetPackが含まれるようになります。

Google Play Pluginに含まれるPlay Asset Delivery Unity APIというライブラリを使用しますが、一部コードを書き換えます。
お行儀が悪いですが、Unityエディタの専用メニューからビルドするようにしか作らないGoogleさんが悪い。嘘です、ライブラリがあるだけでもとても助かります。


## 検証環境

* Unity 2019.4.22f1
* Google Play Plugin ver 1.4.0

## コード


### AppBundleBuilderを修正する

##### 1. AndroidPlayerFilePathをpublicにする

Before

```csharp:AppBundleBuilder.cs
private string AndroidPlayerFilePath
{
    get { return Path.Combine(_workingDirectoryPath, AndroidPlayerFileName); }
}
```

After

```csharp:AppBundleBuilder.cs
public string AndroidPlayerFilePath
{
    get { return Path.Combine(_workingDirectoryPath, AndroidPlayerFileName); }
}
```

##### 2. BuildAndroidPlayerメソッドの冒頭にあるディレクトリ作成処理をメソッドに切り出す

Before

```csharp:AppBundleBuilder.cs
public virtual bool BuildAndroidPlayer(BuildPlayerOptions buildPlayerOptions)
{
    var workingDirectory = new DirectoryInfo(_workingDirectoryPath);
    if (workingDirectory.Exists)
    {
        workingDirectory.Delete(true);
    }

    workingDirectory.Create();

       :
       :


```

After

```csharp:AppBundlePublisher.cs

public void EnsureWorkingDirectory()
{
    var workingDirectory = new DirectoryInfo(_workingDirectoryPath);
    if (workingDirectory.Exists)
    {
        workingDirectory.Delete(true);
    }

    workingDirectory.Create();

}

public virtual bool BuildAndroidPlayer(BuildPlayerOptions buildPlayerOptions)
{
    EnsureWorkingDirectory();

```

### AppBundlePublisher.csを修正する

AppBundlePublisherの適当な箇所にメソッドを追加します。
もしかしたらSystem.IOあたりのusingを追加する必要もあるかもしれません。


```csharp:AppBundlePublisher.cs

public static void PackAsset(string aabFilePath, AssetPackConfig config)
{
    var appBundleBuilder = CreateAppBundleBuilder();
    if (!appBundleBuilder.Initialize(new BuildToolLogger()))
    {
        return;
    }
            
    appBundleBuilder.EnsureWorkingDirectory();
    File.Copy(aabFilePath, appBundleBuilder.AndroidPlayerFilePath, true);
            
    Debug.LogFormat("Building app bundle: {0}", aabFilePath);
    appBundleBuilder.CreateBundle(aabFilePath, config);
}

```

### ポストプロセスビルド処理を追加する

適当なクラス名でIPostprocessBuildWithReportを実装します。

```csharp
public class PublishPlayAssetDelivery : IPostprocessBuildWithReport
{
    public int callbackOrder => 0;

    public void OnPostprocessBuild(BuildReport report)
    {
        if (report.summary.platform != BuildTarget.Android)
        {
            return;
        }

        var config = AssetPackConfigSerializer.LoadConfig();
        AppBundlePublisher.PackAsset(report.summary.outputPath, config);
    }
}
```

## 最後に

Googleさんが提供している専用のビルドメニューでは下記のような動作をしています。

1. AppBundleをビルドしてテンポラリディレクトリに出力する
1. AssetPackをビルドする
1. AppBundleを解凍して、必要なAssetPackを組み込む
1. 再度パッキングして、本来の出力先に保存する

上記の手続きが一連の流れとしてコーディングされていて、自分にとって都合が悪かったため、今回は3と4を抜き出してみました。
Djangoでマイグレーションを使っていないプロジェクトでマイグレーションを導入する

# はじめに
プロジェクトの途中からDjangoのマイグレーション機能を使うようにした際のメモです。
Djangoのバージョンは2.0を使ってます。

# models.pyを作る
まず、DBの構造を定義してあるmodels.pyを作る必要があります。
models.pyは既存のスキーマ情報から逆生成します。

```shell
$ python manage.py inspectdb > models.py
```

これで、models.pyが生成されるので、見てみるとスキーマの情報が記載されていると思います。
あとは、マイグレーションで管理をするので、`managed = False` を消していくだけになります。

# マイグレーションファイルを作る
models.pyができたので、次にマイグレーションファイルを生成していきます。
下記のコマンドを実行すると `0001_initial.py` のマイグレーションファイルができます。

```shell
$ python manage.py makemigrations ${app_name}
```

# マイグレーションを実行する
マイグレーションファイルができたので、マイグレーションを実行していきます。
基本的には、

```shell
$ python manage.py migrate ${app_name}
```

のコマンドでマイグレーションを実行しますが、今回の場合は、すでにテーブルが存在するので、
`--fake-initial` オプションを使って初回のマイグレーションをダミーで流します。

```shell
$ python manage.py migrate ${app_name} --fake-initial
```

これで、移行作業は終わりになります。
あとは、適時、 `models.py` を修正して、 `makemigrations` でマイグレーションファイルを作成していく流れになります。
ぼっち演算子とtryメソッドの違い

# 共通点
レシーバがnilの場合は、nilを返す

```ruby
foo = nil

foo.try(:bar)
#=> nil

foo&.bar
#=> nil
```

# 相違点
- レシーバがnilで無く、レシーバが呼び出せないメソッドを呼び出してしまった場合
    - ぼっち演算子: NoMethodErrorを返す
    - tryメソッド: nilを返す

```ruby
# レシーバが呼び出すこの出来ないbarメソッドを呼び出した場合

foo&.bar
#=> NoMethodError

foo.try(:bar)
#=> nil
```

# まとめ
必ずしも、似てはいるけど同じでは無いってことですね。
WSL2にpyenvとpipenvによるpython仮想環境構築

# 導入
WSL2のubuntuにpypenvとpipenvを導入し、仮想環境構築を目指します。
# 環境
+ WSL2
+ ubuntu 20.04

# 手順
+ pip3のインストール
+ pyenvのインストール
+ pipenvのインストール
+ 仮想環境の実行

# インストール
まずはpip3のインストールから行います。インストール出来たかは`pip3`で確認できます。

```
sudo apt install python3-pip
pip3 
```
次にpyenvのインストールを行います。まずは依存関係のあるライブラリからインストールします。詳細は[こちら](https://github.com/pyenv/pyenv/wiki#suggested-build-environment)になります。
そして`git clone`をします

```
sudo apt-get install make build-essential libssl-dev zlib1g-dev \
libbz2-dev libreadline-dev libsqlite3-dev wget curl llvm \
libncursesw5-dev xz-utils tk-dev libxml2-dev libxmlsec1-dev libffi-dev liblzma-dev

git clone https://github.com/pyenv/pyenv.git ~/.pyenv
```

次にPATHを通します。私は`.bashrc`の追記しました。

```
export PYENV_ROOT="$HOME/.pyenv"
export PATH="$PYENV_ROOT/bin:$PATH"
eval "$(pyenv init --path)"

source .bashrc
```

動作確認をします。`pyenv install --list`と入力すると、使用できるバージョンが出てきます。Pythonは最初に数値だけ表示されています。

```
pyenv install --list
Available versions:
  以下に使えるバージョン
```
自分が使用するバージョンをインストールしてください。インストールされたバージョンの確認は`pyenv versions`で、実際に使うバージョンの確認は`pyenv version`で可能です。使用するバージョン指定は`pyenv global バージョン`でできます。
現在どのバージョンを使用できるのかは冒頭に`*`がついているので確認できます。

なお`3.8.5`は先に筆者がインストールしたものになります。

```
pyenv install 3.9.0
//少し時間かかります
Downloading Python-3.9.0.tar.xz
~
Installed Python-3.9.0 to /home/user/.pyenv/version/3.9.0

pyenv versions
* system(set by /home/user/.pyenv/version)
  3.8.5
  3.9.0

pyenv global 3.9.0

pyenv version
  system
  3.8.5
* 3.9.0(set by /home/user/.pyenv/version)
```
次にpipenvです

```
pip3 install pipenv
```

次に仮想環境の構築を行います。`pipenv shell`を入力すると仮想環境に入れます。まず仮想環境を作成したいディレクトリに移動します。

```
mkdir test

cd test
```
仮想環境の作成を行います。作成方法は`pipenv --python バージョン`で可能です。

```
pipenv --python 3.9.0
```
成功すると`Pipfile`が作成されます。そして仮想環境を有効化するには`pipenv shell`になります。

```
pipenv shell
```
すると、左側にディレクトリ名が追加され、仮想環境が有効化されます。この環境下で自身で実行したいプログラムを実行します。

```
(test) username@hostname /test$ 
```
仮想環境を抜ける場合は以下でいけます。

```
exit
```
仮想環境の削除はこちらです。

```
pipenv --rm
```

以上がWSL2でpyenvとpipenvによるpython仮想環境の構築から有効化までの流れになります。
より詳しい事については、[こちら](https://rinatz.github.io/python-book/ch04-05-pipenv/)が参考になります。

# 参考文献

[Ubuntu(WSL)にpyenvとPipenvの環境を構築する](https://www.beeete2.com/blog/?p=2690)

[WSL+pyenv+pipenv+VSCodeで令和モダンなpython仮想環境を構築しよう！](https://highso.hatenablog.com/entry/2020/01/16/180000)
JavaScript 四則演算

##四則演算 まとめ

```javascript
//足し算
console.log(4+2);

//引き算
console.log(4-2);

//掛け算
console.log(4*2);

//割り算
console.log(4/2);

//余り
console.log(4%2);
```

###結果
![スクリーンショット 2021-06-09 20.10.41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/678283/cfb3e376-220a-1a8f-844a-79bf6c090110.png)
SSHポートフォワードでリモートのHTTPSサーバを閲覧する

# TL;DR

リモートのHTTPSサーバーにSSHポートフォワードしてアクセスする時にSSL証明書エラーが出た。ローカルの/etc/hostsでリモートホスト名を127.0.0.1に紐付けると回避できたよ。

# シュチュエーション

パンデミックもありリモートでの仕事が増えているものの、
まだまだリモート環境が前提でない社内システムにアクセスすることがあるかと思います。例えば今回遭遇したサーバーの条件としては以下のような感じでした。

* sshログインができる
* 社外向けのwebページ(ip制限はなし。basic認証あり)
* 社内向けのwebページ(イントラからのみアクセスできるようにip制限をしている)
* グローバルIP及びドメイン名は取得済み

今回問題となったのは3番目の「社内向けwebページ」へのアクセスです。


# 登場人物と条件

* ローカルマシン
* リモートサーバー

リモートサーバのホスト名はremote_host、ipはaaa.bbb.ccc.dddであるとします。また、社内向けwebページへのリモートサーバ自身(aaa.bbb.ccc.ddd)からのアクセスは許可されているとします。

自宅の環境でグローバルIPを持っている人はリモートサーバのip制限を書き換えてアクセス可能にすることが出来るでしょう。しかし僕はそのためだけに固定IPを取りたくはありませんでした。

# 発生したこと

そこで、sshポートフォワードを使ってHTTPSサーバにアクセスしようと考えました。以下のコマンドで出来るだろうと試してみました。

```
ssh -L 8080:remote_host:443 remote_user@remote_host
```

これで以下のようにlocalhost:8080にremote_host:443が紐づいていたので、
https://localhost:8080 にアクセスすれば社内サーバが見られるはずです。

> 127.0.0.1:8080 -> remote_host:443

が、残念なことに証明書エラーが出てしまいました。

# 原因

ブラウザからのメッセージを読んでみると

>「localhostでは、悪意のあるユーザーによって、パスワード、メッセージ、クレジット カードなどの情報が盗まれる可能性があります。」

とのことですので、localhostは信用できないでのアクセスできません、と言われているようです。

なぜ信用できないと言われるかを考えてみます。
そもそもSSL証明書は「アクセスしたサーバが改ざんされていないこと」を証明するものです。そのため、通常はAというサーバにアクセスした時に、
証明書を見せてもらい「Aさんと名乗っている人がAさんであること」を確認することになります。

つまり、今回の状況は
「localhostさんをお願いします」
と言ったら、
「私はremote_serverというものです。認証局さんの保証付きです」
と返事が来たようなものだと理解しています。それは、なんというか普通にダメな感じがします。

# 対応

アクセスしたいのはremote_serverなので、
お願いする時にちゃんとremote_serverさんを指名すれば良いはずです。

しかし普通にremote_serverにアクセスするとDNSで名前解決がおこなわれてしまい、本当にremote_server(aaa.bbb.ccc.ddd)にアクセス要求してしまいます。
そして、アクセス先のサーバーではip制限がかかっているので実際にはアクセスは成功しません。

では今回どうしたかというと、
ローカル側で"remote_server"という名前をローカルマシンの127.0.0.1(localhost)に紐付けることで解決しました。どういう流れになるかというと

> "remote_server":8080 -> 127.0.0.1:8080 -> remote_server:443

これでremote_serverさんをお願いして、remote_serverさんから返事がくることになります。remote_serverを127.0.0.1に結びつけるにはローカルマシンの/etc/hosts(macなら/private/etc/hosts)に以下を追記することで出来ます。

```txt:/etc/host
remote_server 127.0.0.1
```

# 最後に

今回はこの方法で対応したものの、
他の良いやり方があれば是非コメントで教えてください！
Dartのテクニカ - 実装のためのコードスニペット - 

思いつくたびに追加していきます。備忘を兼ねて。

:::note
_Added at: 31st Jul. '22_

「思いつくたびに追加」と銘打ちつつ随時更新詐欺("即死記事"化)をしている現状 (cf: 「随時更新」云々については@nkayさんの記事を参照[^FreqUp])
:::
## 高階関数で括弧乗算

例えば(x-2)(y+3)のように括弧書きで乗算を表記することがありますが、それをコード中で表記できないか、というのがこのコードの趣旨です。関数を返す高階関数だと括弧が連続するので、これは使えるのではないかと思い書いてみました。

```dart
num Function(num) m(num j){
    return (k)=>k * j;
}
```

これで

```dart
//int m = 1;
int x = 2;
int y = 6;
int z = m(x-2)(y+3);
```
と括弧表記した掛け算みたいなことができました。

### 解説

関数を返す関数はこのような構文です

```dart
返り値型 Function(引数1型) 関数名(引数2型 引数){
  return (引数1){2つの引数を使った処理};
}
```

処理じゃなくて式の場合はアロー表記を使って

```dart
返り値型 Function(引数1型) 関数名(引数2型 引数){
  return (引数1)=>2つの引数を使った計算;
}
```
とも書けます

今回の高階関数の場合だと、一度引数を与えて`m(2)`とすると1つのnum型の引数をとってnum型の返り値を返す無名関数`(num k)=>k*2`が返ってきます。

これにもう一回num型の引数を与えることで乗算された結果が返ってきます。

---

[^FreqUp]: [【随時更新】←これがついているQiita記事の4割は随時更新されないという事実](https://qiita.com/nkay/items/189496192b328bb2b5e5 "Qiita: 【随時更新】←これがついているQiita記事の4割は随時更新されないという事実")