OmniAICreator/Qiita-1.07M huggingface dataset:
gunicornをsystemdで自動起動する

#はじめに
gunicornを自動起動しようとしたところ2時間ハマったのでメモ

#環境
- CentOS 8.1
- miniconda 3
- python 3.6
- gunicorn 20.1.0

#前提
- django アプリの場所 /home/kimisyo/helloworld
- wsgiファイルの場所　/home/kimisyo/helloworld_app
- guniconコマンドの場所  /home/kimisyo/minicona3/envs/django/bin/gunicorn

#方法
## 設定ファイル作成
公開ポートは8000としている。

``` /home/kimisyo/helloworld/gunicorn.conf.py
import multiprocessing

bind = "0.0.0.0:8000"
daemon = True
workers = multiprocessing.cpu_count() * 2 + 1
```

## serviceファイル作成

```/etc/systemd/system/gunicorn.service
[Unit]
Description=gunicorn daemon
After=network.target

[Service]
User=kimisyo
Group=kimisyo
WorkingDirectory=/home/kimisyo/helloworld
ExecStart=/home/kimisyo/minicona3/envs/django/bin/gunicorn --config /home/kimisyo/helloworld/gunicorn.conf.py helloworld.wsgi:application
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target
```

## 自動起動設定
```sh
#systemctl enable gunicorn.service
#systemctl start gunicorn
#systemctl status gunicorn
```

うまくいけば以下のような状態になっているはずだ。

```sh
#systemctl status gunicorn
● gunicorn.service - gunicorn daemon
   Loaded: loaded (/etc/systemd/system/gunicorn.service; enabled; vendor preset: disabled)
   Active: active (exited) since Thu 2021-06-03 07:34:56 JST; 8min ago
  Process: 798 ExecStart=/home/kimisyo/yes/envs/django/bin/gunicorn --config /home/kimisyo/helloworld/gunicorn.conf.py helloworld.wsgi:application (code=exited, status=0/SUCCESS)
 Main PID: 798 (code=exited, status=0/SUCCESS)
    Tasks: 4 (limit: 11492)
   Memory: 110.4M
   CGroup: /system.slice/gunicorn.service
           ├─1028 /home/kimisyo/yes/envs/django/bin/python /home/kimisyo/yes/envs/django/bin/gunicorn --config /home/kimisyo/helloworld/gunicorn.conf.py helloworld.wsgi:application
           ├─1051 /home/kimisyo/yes/envs/django/bin/python /home/kimisyo/yes/envs/django/bin/gunicorn --config /home/kimisyo/helloworld/gunicorn.conf.py helloworld.wsgi:application
           ├─1054 /home/kimisyo/yes/envs/django/bin/python /home/kimisyo/yes/envs/django/bin/gunicorn --config /home/kimisyo/helloworld/gunicorn.conf.py helloworld.wsgi:application
           └─1058 /home/kimisyo/yes/envs/django/bin/python /home/kimisyo/yes/envs/django/bin/gunicorn --config /home/kimisyo/helloworld/gunicorn.conf.py helloworld.wsgi:application

 6月 03 07:34:56 localhost.localdomain systemd[1]: Started gunicorn daemon.
```

#最大のポイント
最大のポイントは、```gunicorn.service```　ファイルに```RemainAfterExit=yes``` を入れることである。これがないと起動してもすぐに停止してしまう。
【Javascript】Mapオブジェクト（iteration）

# 初めに
Mapオブジェクトについて学習した内容のoutput用記事です。

※内容に間違いなどがある場合はご指摘をよろしくお願いします。
※こちらの記事はあくまでも個人で学習した内容のoutputとしての記事になります。

前回の記事：
https://qiita.com/redrabbit1104/items/cc0d851da2a533cda694

# Mapオブジェクトの生成
setメソッドを使わずにMapオブジェクトは以下のような方法で作れます。

```javascript
  const bookStore = new Map([
        ["mon", { open: 10, close: 20 }],
        ["tue", { open: 11, close: 19 }],
        ["sun", { oepn: 0, close: 20 }],
      ]);

      console.log(bookStore);
//Map(3) {"mon" => {…}, "tue" => {…}, "sun" => {…}}
```

# ObjectからMapオブジェクトへ
Mapの引数は配列の中に配列が入っている構造ですので、Objectのentriesメソッドで生成したものを丸ごとMapの引数にすればObjectからMapオブジェクトに簡単に変換することができます。

```javascript
   const bookStore = {
        mon: { open: 10, close: 20 },
        tue: { open: 11, close: 19 },
        sun: { open: 0, close: 20 },
      };
      const entries = Object.entries(bookStore);
      console.log(entries);
      //(3) [Array(2), Array(2), Array(2)]

      const newMap = new Map(entries);
      console.log(newMap);
      //Map(3) {"mon" => {…}, "tue" => {…}, "sun" => {…}}
```

https://qiita.com/redrabbit1104/items/e054cdee78873980761e

# for of文を使ったloop

また、for ofを使ってkeyの値に該当するvalueだけをコンソールに表示することもできます。

```javascript
 const items = new Map([
        ["name", "John"],
        [1, "school"],
        [2, "home"],
        [true, "Yes"],
        [false, "No"],
      ]);

      for (const [key, value] of items) {
        if (typeof key === "number") 
        console.log(`Guess ${key}: ${value}`);
      }]
      //Guess 1: school
      // Guess 2: home
```
typeofでキーの値が数字だけの場合に値を出力することができました。

# Mapオブジェクトを配列にする

Spread構文を使えば、Mapオブジェクトを配列にすることもできます。

```javascript
  　　　　　　　console.log([...items]);
      //(6) [Array(2), Array(2), Array(2), Array(2), Array(2), Array(2)]

      console.log([...items.entries()]);
      //(6) [Array(2), Array(2), Array(2), Array(2), Array(2), Array(2)]

      console.log([...items.keys()]);
      //(6) ["name", 1, 2, "正解", true, false]

      console.log([...items.values()]);
      //(6) ["John", "school", "home", 2, "Yes", "No"]
```

# 参考サイト
https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Global_Objects/Map
クラスメソッドとインスタンスメソッド

わかっているようでわかっていなかった。
今まで知ったかぶりしていた自分にお別れを告げるべく、
なんとなくスルーしていたクラスメソッドとインスタンスメソッドの違いについて解説していけたらと思う。
私は確かに知識レベル最底辺だが、
それでも私より理解できてない人はたくさんいる。
備忘録としても機能するだろう。
間違いがあった場合は、
どなたか指摘していただけると幸いです。

・クラスメソッド

```class.rb
class Character
  # インスタンス変数
  attr_accessor :hp, :power

  def initialize(hp, power)
    self.hp = hp
    self.power = power
  end

  # self.name として呼ばれるが、実際には Slime や Hero の name が呼び出される。
  # この name は呼び出されないので、 '' を返すだけにしている。
  def name
    ''
  end

  def attack(character)
    character.hp -= self.power
    puts "#{self.name}が#{character.name}を攻撃して#{self.power}ポイントのダメージを与えた！"

    if character.hp <= 0
      self.defeat(character)
    end
  end

  def defeat(character)
    puts "#{self.name}は#{character.name}を倒した！"
  end
end

class Slime < Character
  # クラス変数
  # クラスの種類そのものなので、最初から代入して、以後変更しない
  @@type = 'スライム'

  # インスタンス変数
  attr_accessor :suffix

  def initialize(suffix)
    super(10, 3)
    self.suffix = suffix
  end

  def name
    # この Slime クラスのクラス変数 type ('スライム') を返す
    @@type + self.suffix
  end

  # クラスメソッド
  def self.description
    puts @@type + 'は、最弱のモンスターだ！'
  end
end

class Hero < Character
  # クラスの種類そのものなので、最初から代入して、以後変更しない
  @@type = '主人公'

  def initialize
    super(1000, 30)
  end

  def name
    # インスタンス変数ではなく、クラス変数を呼び出している
    @@type
  end

  def self.description
    puts @@type + 'は、この世界を守る勇者だ！'
  end
end

hero = Hero.new
slime_A = Slime.new('A')

slime_A.attack(hero)
hero.attack(slime_A)

Hero.description
Slime.description
```

このように、
メソッド定義時のメソッド名の前に self. を付けることでクラスメソッドとなる。

・インスタンスメソッド
クラス内で定義されたメソッドを、インスタンスメソッドと呼びます。先のコードでいうと、initialize() や attack() はインスタンスメソッドです。

```class.rb
class Person
  def self.class_method
    puts 'これはクラスメソッド'
  end

  def instance_method
    puts 'これはインスタンスメソッド'
  end
end

# 使う時

Person.class_method
# これはクラスメソッド

tanaka = Person.new(name: 'tanaka')
tanaka.intance_method
# これはインスタンスメソッド
```
ファイルを変更せずにもう一度git pushがしたい

<h1>はじめに</h1>
一度、リモートリポジトリにpushしたファイルを、変更せずに再度pushしたいと思ったことはありませんか？

私はあります。（詳細は下の「背景」へ）

でも、ファイルに変更がないので、commitがない。そうなるとpushもできないかと思います。
今回の記事では、ファイルを変更せずにもう一度pushする方法をご紹介します。


<h1>背景</h1>
いつものようにリモートリポジトリにファイルをpushしたところ、pushしたファイルはリモートリポジトリに反映されているものの、いつも動いてくれるCircleCIが動いてくれない。

CircleCIの設定は変更していないので、アプリ側の問題ではないと考え、再度pushを試してみたいと思ったものの、ファイルを変更していないので、当然commitもなくpushができない。

さぁ、どうしたものか。


<h1>方法</h1>
空のcommitをすることで再度pushをすることができるようになります。

入力したコマンドは次のとおりです。

```
git commit --allow-empty -m "コミットメッセージ"
```

あとはいつもどおり、pushをするだけです。

```
git push リモートリポジトリ名 ブランチ名
```

<h1>さいごに</h1>
私の場合は、この方法により再度pushをすることで、CircleCIがきちんと動いてくれ、一件落着となりました。（最初に動かなかった理由は不明ですが…）

この方法のデメリットとして、多用すると意味のないコミット履歴が増えていくことになるので、ご注意ください。

そもそも、ファイルを変更せずにpushしたいというニーズがあるかは疑問ですが、この記事が誰かの参考になれば幸いです。
Google Colab GPU使用時のトラブル対応

### CatBoostError: Multiple eval sets are not supported on GPU

```
model = CatBoostRegressor(task_type='GPU')

model.fit(X_train,
          y_train,
          eval_set=[(X_train, y_train), (X_valid, y_valid)], # これが良くないらしい 
         )
```

eval_set の行を削除したら、エラーで止まらずに動作しました。
C#　テキストファイルの保存 便利なCSV

 ***ファイルの保存***
NUll確認やファイルの存在確認を利用して細かくエラーハンドリングしながらファイル操作を行うのは色々と気を遣います。
Fileクラスで保存する場合、Windowsのように(1),(2),,,を末尾につけて自動でインデックスは振ってくれないので同名のファイルが存在していても平気で上書きします。そこで、ファイルがいたらインデックスをつけて新しくファイルを作る方法を紹介します。

string sの中身は「,」区切りの文字列であればよくCSVも同じテキストファイルなので拡張子をcsvにすればOK 
あとは出来たファイルをExcelかGoogleSpreadSheetでインポートすれば素敵な表が瞬時に作れます。
メモ帳で開いて中身を確認することもできるのでデータの抜き取りやＨＴＭＬの解析などに使い勝手が良いです。
これだけのためにフォームアプリを利用する気にはならないのでコンソールアプリで開発するひとには必須です。

次のコードはメソッドで後からメイン側で呼び出せるようにしています。

```sample.cs
using System;
using System.IO;


      private static void SaveFile(string s)
        {
            string DesktopDir = System.Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory);
            string FileName = "MJ_Resultlist";
            string Extend = ".csv";
            string FilePath = DesktopDir + "\\" + FileName + Extend;
            //上記の別の書き方
            //string FilePath = Path.Combine(DesktopDir,FileName) + Extend;
　　　　　　 //コメントでいただきましたメソッドです。フォルダ階層が深い場合は有効そうですね。
            

            int FileIndex = 0;

            //上書しないよう被らないファイル名になるまでループ
                while (File.Exists(FilePath) == true)
                {
                    FileIndex++;
                    FilePath = DesktopDir + "\\" + FileName + "(" + FileIndex.ToString() + ")" + Extend;
                }

            //　文字列をファイルに保存
            if (string.IsNullOrWhiteSpace(s) == false)
                File.WriteAllText(FilePath, s);
            else
                Console.WriteLine("ファイル保存失敗");
        }
```


引数sの中身の代入例としては　

```sample1.cs
string s = "A" +","+ "B" +","+ "C";
```

と書いても良いですが、使い勝手が悪いので

```sample2.cs
var list = new List<string>();
list.Add("A");
list.Add("B");
list.Add("C");
string s = string.join(",",list);
SaveFile(s);

//出力
/*********
A,B,C
*********/
```
のほうが見やすいです。また、CSVファイルの場合、改行コード"\n"を入れることで
段替えをおこなうことができます。

```sample3.cs
var listA = new List<string>();
listA.Add("A1");
listA.Add("A2");
listA.Add("A3");

var listB = new List<string>();
listB.Add("B1");
listB.Add("B2");
listB.Add("B3");

var listC = new List<string>();
listC.Add("C1");
listC.Add("C2");
listC.Add("C3");

string A = string.join(",",listA);
string B = string.join(",",listB);
string C = string.join(",",listC);
string s = A + "\n" + B + "\n" + C;
SaveFile(s);

//出力
/*********
A1,A2,A3
B1,B2,B3
C1,C2,C3
*********/
```


**ディレクトリの環境依存**
提供先が誰に渡るか分からない場合、いちいちPCのユーザー名を聞き出してディレクトリにしてしまうのはよくありません。このソフトがどの環境で使用されてもいいようにSystemクラスには環境を呼び出すクラスが用意されています。次のコードは環境のデスクトップを呼び出しますのでどのPCでプログラムを実行してもそのデスクトップに保存されます。
*System.Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory)*

ここからフォルダを自動生成して中に保存することもできます。


**呼び出し**
ファイルの保存は基本的に非同期処理が好ましく、フォームアプリならプログラムのセッションはソフト終了まで続くので例えばセーブボタンを押してから保存完了まで操作を受け付けないというのは望ましい動作とは言えません。
しかし、今回はコンソールアプリなのでセッションが終わると非同期処理も途中で落ちてしまいます。
そこでWait()を使ってタスク完了まで待ち、完了したらセッションを閉じるようにしています。
（最初から非同期にしなければ良いと思うかもしれませんがコードに汎用性を持たせるため）

メインで呼び出すときは、次のようなコードになります。

```Main.cs
using System.Threading.Tasks;

           // ファイルの保存（別タスクで非同期処理　続けて処理をおこなうときはWait()を削除する）
            Task task1 = Task.Run(() =>{  SaveFile(resultstr);  });
            task1.Wait();
```
【django】DateTimeField %s received a naive datetimeというwarningがでたときの対処法


ワーニングなので特に問題はないんだろうけど鬱陶しいのでどうにかしたい人生でした。

## 結論

```settings.py
LANGUAGE_CODE = 'ja'

TIME_ZONE = 'Asia/Tokyo'

USE_I18N = True

USE_L10N = True

USE_TZ = False <- 多分デフォだとTrueなのでFalseにする
```

ただこうするのはあまり良くないとか知らないおじさんが書いてたりしたんですけど言ってる意味がよくわからなかったので僕はこれでことなきを得ることしました。
Airtableみたいな機能クラウド型データベースツールが他にないか調査してみたメモ

# ことの発端
ちょっと個人利用目的で1個Webアプリを作りたいなと思って、どんな仕組みにしようかなーと考えてました。
で、「よーし流行りのGraphQLでデータを返してReactで作るかー」と思って、じゃあデータをどこに格納しようかなーと考えてたんですが、あんまりガリガリ作ったりするのもやだし、データベース作らないといけないので編集とかしやすいのないかなーと考えて、「そうだAirtableにしよう」と思いつきました。

実はAirtable、GraphQLも対応してます。
正確にいうと「BaseQL」というサービスを経由するのですが…

https://www.baseql.com/


これで…

1. Airtableでデータを保持する
1. Airtableとアプリ側の接続インターフェースはbaseQLを利用してGraphQL接続で
1. アプリ側はReactベースの何かで接続して作る


これでうまくいきそうだ！と思ったんですが…ちょっと…高い…
このBaseQLとかのApps機能を使おうとすると20$/month（年払いで）なんですよね。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/443/c3dae85d-a88d-0365-c3e4-01cdaac4c4d0.png)

なので、年間240$はちょっと高いなと思って…躊躇。
なんか似たような代替サービスないかなーとおもってちょっと探してました。
で、調査してみたメモがこちらとなります。（前置きが長い）



# 調査してみたサービス

## Airtable
Airtableはノーコード＋クラウド型データベースサービスになります。
イメージはデータベースを非エンジニアでも使いやすく、管理画面をくっつけてくれた感じ。

https://airtable.com/


こんな感じでおしゃれな画面も提供されてデータ管理がしやすい。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/443/563b979c-da71-a68c-57d6-fe56655866c9.png)

もちろんこれにいろんな機能がついてて、REST API等使ってデータを取り出すことが可能です。
この編集画面も結構秀逸でちゃんとコピペや計算処理、別テーブルデータからのLookupも可能です。

https://airtable.com/api

まぁやはりこれ系サービスの雄ではあります。

## Google Spreadsheet
ん、表計算のツールここで出すんかい！という話ですが、Airtableがデータベース側からインターフェースとか便利な機能を盛り込んでいったのであれば、Google Spreadsheetは表計算アプリからデータベース側に歩み寄ってる感じ。

Google SpreadsheetでAPIできるんかい！ってことですができます。

https://qiita.com/takatama/items/7aa1097aac453fff1d53


なんせ無料ですしね…ある意味管理画面は当然のごとくついてます。
ただ、リクエスト制限が結構あります。

## baserow
オープンソース＋無料？でホスティングもあるAirtableと同じ思想のノーコードデータベースアプリ。

https://baserow.io/

画面も似てるしやれることも似てます。
中身のアーキテクチャはDjangoとNuxt.js＋PostgreSQLの模様。

https://gitlab.com/bramw/baserow

オープンソースなので置けばタダというのはいいっちゃいいですね。
管理画面は最低限の機能はある感じ。ただ、Airtableほどの機能は全然ないです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/443/70ec5e57-cbed-f1ee-4fa1-4439dbc2d444.png)


これからだなぁという感じ。


## NocoDB
これもオープンソースで開発してる同じようなソリューション。

https://www.nocodb.com/

ここはホスティングサービス無いので自分で設置です。
Herokuとかに展開すればとりあえず使えます。

NocoDBの特徴は、最初から作る時のProjectの外部インターフェースでGraphQLが使えるところ。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/443/328b36c0-5e7d-8e00-c860-97767223307d.png)


そして機能もbaserowよりも豊富です。カラム定義も多いし、インターフェースとしてこっちの方がいい感じ。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/443/aa47ccf0-aaea-4e76-429b-26ed938a35c4.png)


# ということで調査結果

難しいな…Airtable優秀だな…という結果に。
素直にREST APIでAirtableを使おうかな…。

| サービス名 | 金額体系 | データ編集機能 | 周辺機能 | 接続IF機能 | Import/Export | 制限 |
|:-:|:-:|:-:|:-:|:-:|:-:|:-:|
| Airtable  | × (Free〜)<br> GraphQLとかを使おうとすると月20$〜 | ◎ コピペや多くのデータタイプに対応 | ◎ Apps機能で色々追加可能(ただし有料)  | ○ Apps機能使えばGraphQL、DefaultでREST API | ◎ CSV ExportやImport対応 |  ？ 特に無い模様 |
| Google Spreadsheet | ○ 基本無料  | ◎ 文句なし  | ◎ 一通りの機能あり  | ○ 連携できるのいっぱい。GAS使える  | ○ Excelファイル等 | △　同時リクエスト数30やFetchサイズ制限がありややこしい |
| baserow  |  ○ 設置する場所次第 | △ やや使いにくい。データタイプも基本のみ  | △ あまり周辺機能なし | △ REST APIのみ | × Exportのみ | ○ 設置する場所次第|
| NocoDB | ○ 置く場所次第 | ○ 最低限必要なのは揃ってる感 | △ Webhook機能やZapierなどとの連携が可能 | ○GraphQLとREST API選べる | △ やや特殊だができる模様 | ○ 設置する場所次第 |

:::note info
2022/05/11：追加
昨今この領域はCloudCMSと呼ばれる製品群も似たようなサービスになります。
Contentfulとか。かなり高機能にデータを格納することができるものの、割とお高いので使い分けですね。
:::
AsanaとGoogle Apps Scriptを連携する、使い方編

こんにちは、な～です。

今日は、前回紹介した、AsanaManagerオブジェクトを使ってみましょう！
代表的なものを紹介します。

タスクの読み込み

```js
/**
 * テスト用タスクの読み込み
 */
function read() {
  const token = '';
  const taskId = '';

  //オブジェクトを作成する
  const asanaManager = new AsanaManager(token);
  //タスクIDのデータを取得する
  console.log(asanaManager.getTaskData(taskId));
}
```
タスクの作成

```js
/**
 * タスクの作成
 */
function create() {

  const token = '';

  const workspaceId = '';
  const projectId = "";
  const name = '追加したいタスク名';
  const planText = 'タスクの内容！！！！！！';
  const tanto = ''; //IDで指定

  const objTask = {
    "data": {
      "workspace": workspaceId,
      "projects": [projectId],
      "name": name,
      "notes": planText,
      "assignee": { "gid": tanto, "resource_type": "user" }
    }
  };
  //オブジェクトを作成する
  const asanaManager = new AsanaManager(token);
  //処理を呼ぶ
  console.log(asanaManager.createTask(objTask));
}
```
セクションの移動

```js
/**
 * セクションの移動
 */
function move() {
  const token = '';
  const sectionId = '';
  const taskId = '';

  //オブジェクトを作成する
  const asanaManager = new AsanaManager(token);
  const objSetSection = {
    "data": {
      "task": taskId
    }
  };
  asanaManager.addTaskToSection(sectionId, objSetSection);
}
```
サブタスクを作成する

```js
/**
 * サブタスクを作成する
 */
function subTask() {
  const token = '';
  const taskId = '';
  const workspaceId = '';
  const name = '追加したいタスク';
  const planText = 'タスクの内容！！！！！！';
  const tanto = '';


  const objSubtask = {
    "data": {
      "workspace": workspaceId,
      "name": name,
      "notes": planText,
      "assignee": { "gid": tanto, "resource_type": "user" }
    }
  };
  const asanaManager = new AsanaManager(token);
  asanaManager.createSubtask(taskId, objSubtask);
}
```
タスクの更新

```js
/**
 * タスクの更新
 */
function update() {
  const token = '';
  const taskId = '';
  const tanto = '';

  const objUpdateTask = {
    "data": {
      "notes": '更新するよ！',
      "assignee": { "gid": tanto, "resource_type": "user" }
    }
  };
  //オブジェクトを作成する
  const asanaManager = new AsanaManager(token);

  //処理を呼ぶ
  asanaManager.updateTask(taskId, objUpdateTask)
}
```

こんな感じでAsanaを操作できます。
【小ネタ】Universal Render Pipeline/UnlitシェーダのSurfaceModeをスクリプトからTransparentに変更する方法

動的にMaterialを作成した後で、半透明化する設定方法が、調べてもなかなか見つからなかったので、メモしておきます。

```cs:マテリアル作成csファイルの一部
material = new Material (Shader.Find ("Universal Render Pipeline/Unlit"));
material.SetFloat("_Surface", (float)BaseShaderGUI.SurfaceType.Transparent);
BaseShaderGUI.SetupMaterialBlendMode(material); //<-これが大事！
```
BaseShaderGUI.SetupMaterialBlendMode()を呼ばないと所定のBlandModeなどの設定が適用されないのでご注意。

ただ、BaseShaderGUIはUnityEditor用なのでEditorではない環境に向けては、BaseShaderGUI.SetupMaterialBlendMode()の中身を引っ張てくる必要が有ります。
という事で、Runtimeで行いたい場合はこちら。

```cs
material = new Material(Shader.Find("Universal Render Pipeline/Unlit"));
// Alpha Blend
material.SetFloat("_SrcBlend", (float)UnityEngine.Rendering.BlendMode.SrcAlpha);
material.SetFloat("_DstBlend", (float)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
material.DisableKeyword("_ALPHAPREMULTIPLY_ON");
// General Transparent Material Settings
material.SetOverrideTag("RenderType", "Transparent");
material.SetFloat("_ZWrite", 0.0f);
material.renderQueue = (int)RenderQueue.Transparent;
material.renderQueue += material.HasProperty("_QueueOffset") ? (int)material.GetFloat("_QueueOffset") : 0;
material.SetShaderPassEnabled("ShadowCaster", false);
```
AlphaBlend以外のブレンディングが必要な場合は、別途切り替える必要が有りますが、まぁそこはBaseShaderGUI.SetupMaterialBlendMode()を見た方が早いということで。。
【Kotlin】関数まとめ 

#■基本関数
能力をまとめておくもの

引数の渡し方
■名前つき引数
引数名をしっかりと書く何をどこに渡しているか確認しやすい！
hoge(a=1,b=2)

■実引数
引数名を省略 簡潔に書ける。
hoge(1,2)

■引数が複数の場合先頭から渡している。
この場合初めの引数のみ渡している。メソッドの引数にデフォルト値が入っている場合に限る。
hoge(1)


``` kotlin
//基本の書き方
fun hoge(name: String) {}

//戻り値を持たせる書き方
fun hoge2(a: Int, b: Int):Int {
  return a + b
}

//能力が一つなら = で書ける。戻り値もreturn不要
fun hoge3(a: Int, b: Int):Int = a + b

//引数に値をデフォルトで持たせる事ができる。
fun hoge4(a: Int=2, b: Int=3):Int = a + b
//引数に値を渡さないとデフォルト値が働く
hoge4() //結果: 5
//デフォルト値が働かない
hoge4(5,5) //結果: 10
//後半のデフォルト値のみ働く
hoge4(5) //結果: 8


//必須引数(値を持っていない)と任意引数(デフォルトで値をもった引数)混在する場合順番は必須引数から書く
fun hoge3(a: Int, b: Int=3):Int = a + b

```


#■可変長引数
基本仮引数には一つの仮引数に対して一つの値を入れる。

可変長引数は一つの仮引数に対して複数の値を代入でき配列となる。
仮引数にvarargをつける。
for文と相性が良い

``` kotlin
fun hoge(vararg values: Int): Int {
  var count = 0
  //引数で渡された配列になる値をfor文で全て書き出しcountに一つずつ足している。
  for (value in values) {
  count += value
 }
return count
}
println(hoge(4,5,6,1))
//結果 16

```

###■可変長引数と普通の引数を混在する事も可能です。
その場合実引数のみではどこからどこが普通の引数でどこからどこが可変長引数なの？
と言う問題になるなと感じました。
なので混在する場合はなるべく名前付き引数で渡すのがいいのではないかと感じました。

``` kotlin
fun hoge(a: Int, vararg values: Int): Int {
  var count = 0
  //引数で渡された配列になる値をfor文で全て書き出しcountに一つずつ足している。
  for (value in values) {
  count += value
 }
return count * a
}

//実引数のみ
println(hoge(3,4,5,6,1))
//名前付き引数込み
println(hoge(a=3,4,5,6,1))
//結果 16
```

###■可変長引数の引数に配列そのものを渡したい場合
スプレット演算子を使う
配列が入った変数を引数に渡す時に*をつける。

``` kotlin
fun hoge(vararg values: Int): Int {
  var count = 0
  //引数で渡された配列になる値をfor文で全て書き出しcountに一つずつ足している。
  for (value in values) {
  count += value
 }
return count
}

val aaa = intArrayOf(4,9,6,7)
println(hoge(*aaa))
//結果: 26

//配列以外にも一緒に渡せる。
println(hoge(5,6,*aaa))
//結果: 37
```

#■複数の戻り値を指定することも可能　Pair Triple
基本戻り値は一つですが
PairかTripleを使えば複数戻り値を指定する事ができます。

■Pair
戻り値2つ

■Triple
戻り値3つ

``` kotlin
//必ずしも戻り値分の仮引数が必要と言うわけではない
fun hoge(a: Int, b: Int):Pair<Int,Int> {

   return Pair(a,b)
}

//分解宣言
//戻り値が入る。
val(a,b) = hoge(4,5)
println(a) //結果: 4
println(b) //結果: 5
```

■分解宣言
戻り値に返す値分の変数の入れ物を用意する。
書き方
val (a,b) = メソッド名(4,5)
メソッドの戻り値を先頭から順に変数に入れる。
この場合aには4をbには5を

そして使う時は変数を分けているので使いたい返り値のみを使えたりする。

TripleはPairの3つバージョン

■可変長引数を使って複数の戻り値を指定してみた

``` kotlin

fun hoge(vararg values: Int): Pair<Int,Int> {
   var count = 0
   var count2 = 0
   for (value in values) {
    count +=value
    count2 ++
  }
 //必ずしもPair(この中が直接引数を必ずしも書くわけではない。)
 return Pair(count, count - count2)
}

//sumとsum2にはhoge()の戻り値がそれぞれ入る。
val(sum,sum2) = hoge(5,4,2,1)
//戻り値count
 println(sum) //結果: 12
//戻り値count-count2
 println(sum2) //結果: 8

```

■戻り値が複数指定されたとしても一つしか使わない場合
引数の変数名にアンダーバーを指定する。

``` kotlin
val(a,_) = hoge(3,5,6,7)
```
vue3で生のchart.jsを使いグラフを表示する

## vue-chartjsのvue3対応について

悲しいことにvue-chartjsは今のところvue3に対応していないようです。(2021年6月時点)
今は時間がたりないとのことです。
https://github.com/apertureless/vue-chartjs/issues/637
https://github.com/apertureless/vue-chartjs/issues/661

##前提

[Chart.jsのドキュメントのトップぺージ](https://misc.0o0o.org/chartjs-doc-ja/)にあるサンプルをネタにして動かしていきますー。

## バージョン
chart.js: 3.3.2
vue: 3.0.0

## インストール

```bash
yarn add chart.js
```

## コード
```Chart.vue
<template>
    <canvas id="chart"></canvas>
</template>

<script>

//記事末尾で補足
import Chart from 'chart.js/auto';

export default {
  methods: {
    renderChart() {
      let ctx = document.getElementById("chart");
      new Chart(ctx, {
        type: 'line',
        data:{
          labels: ["赤", "青", "黄色", "緑", "紫", "橙"],
          datasets: [{
            label: '得票数',
            data: [12, 19, 3, 5, 2, 3],
            backgroundColor: [
              'rgba(255, 99, 132, 0.2)',
              'rgba(54, 162, 235, 0.2)',
              'rgba(255, 206, 86, 0.2)',
              'rgba(75, 192, 192, 0.2)',
              'rgba(153, 102, 255, 0.2)',
              'rgba(255, 159, 64, 0.2)'
            ],
            borderColor: [
              'rgba(255,99,132,1)',
              'rgba(54, 162, 235, 1)',
              'rgba(255, 206, 86, 1)',
              'rgba(75, 192, 192, 1)',
              'rgba(153, 102, 255, 1)',
              'rgba(255, 159, 64, 1)'
            ],
            borderWidth: 1
          }]
        },
        options: {
          scales: {
            yAxes: [{
              ticks: {
                beginAtZero:true
              }
            }]
          }
        }
      });
    }
  },
  mounted() {
    this.renderChart();
  }
};
</script>

```

こんな感じでuserしてあげれます。

```Sample.vue
<template>
  <div>
    <h2>chart sample</h2>
    <Chart></Chart>
  </div>
</template>

<script>
import Chart from '../components/Chart';

export default {
  components: {
    Chart,
  },
}
</script>
```

こんな感じの画像になります。
![スクリーンショット 2021-06-03 0.48.14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/320110/13c0163e-d6ae-e983-4b61-978aca8ac266.png)

## 補足

chart.js3では、使用するモジュールを登録する必要があるというように、ドキュメントに記載がありました。

> Chart.js 3 is tree-shakeable, so it is necessary to import and register the controllers, elements, scales and plugins you are going to use.

https://www.chartjs.org/docs/latest/getting-started/integration.html#bundlers-webpack-rollup-etc

以下のように単にchart.jsだけだとインポートするとコンソールエラーが出てしまいます。
なので登録してあげましょう。

```vue
import { Chart } from 'chart.js';
```

> Uncaught (in promise) Error: "linear" is not a registered scale.
> Uncaught TypeError: Cannot read property 'left' of undefined



したがって登録をしてあげます。一個一個必要なものだけを登録方法もいいようですが、ドキュメントに記載してある短い登録フォーマットを使うと動きます。

```vuejs
import { Chart, registerables } from 'chart.js';
Chart.register(...registerables);
```

また上記を１行で実行できる別のパスを用意してくれてると書いてあります。それが楽なので、今回はそちらの書き方を選びました。

```vue.js
import Chart from 'chart.js/auto';
```
Kotlin オブジェクト指向

##オブジェクト指向
オブジェクトとは、物のこと。
指向とは、目的に向かうこと。

オブジェクト指向とは、プログラムを書く前に設計すること。

```kotlin
fun main() {
    var name = "モンスター"
    var hp = 500
    
    println( "${ name }の攻撃！！")
    println( "${ name }は逃げ出した･･･")
    println( "${ name }は倒された･･･")
} 
```

これは、オブジェクト指向ではなく、ただコードを書いただけで必要な変数や関数を並べただけ。
オブジェクト指向にするには、クラスに分けたりすることでやりやすくする。

```kotlin
fun main() {
    val m = Monster()
    m.attack()
    m.escape()
}

class Monster {
    var name:String = "モンスター"
    var hp:Int = 200
    
    fun attack(){
        println( "${ name }の攻撃！！")
    }
    
    fun escape(){
        println( "${ name }は逃げ出した･･･")
    }
    
    fun down(){
        println( "${ name }は倒された･･･")
    }
}
```
上のように、キャラクターや行動ごとなどで分けることで設計をし、やりやすいようにできる。
これをオブジェクト指向という。（他の意見もあるそうですが・・・）
XGBRegressor で WARNING: src/objective/regression_obj.cu:152: reg:linear is now deprecated in favor of reg:squarederror.

## Issue

タイトルのとおり。fit を実行すると以下の warning が出る。

```python
regressor = XGBRegressor(tree_method='gpu_hist', random_state=0)
regressor.fit(X_train, y_train)
```

```
[16:10:12] WARNING: /workspace/src/objective/regression_obj.cu:152: reg:linear is now deprecated in favor of reg:squarederror.
XGBRegressor(base_score=0.5, booster='gbtree', colsample_bylevel=1,
             colsample_bynode=1, colsample_bytree=1, gamma=0,
             importance_type='gain', learning_rate=0.1, max_delta_step=0,
             max_depth=3, min_child_weight=1, missing=None, n_estimators=100,
             n_jobs=1, nthread=None, objective='reg:linear', random_state=0,
             reg_alpha=0, reg_lambda=1, scale_pos_weight=1, seed=None,
             silent=None, subsample=1, tree_method='gpu_hist', verbosity=1)
```

GridSearchCV しようものなら延々出続けるのでうざい。

## 環境

Google Colab

## 解決方法

`objective='reg:squarederror'` を指定する。

```python
regressor = XGBRegressor(tree_method='gpu_hist', random_state=0, objective='reg:squarederror')
regressor.fit(X_train, y_train)
```

```
XGBRegressor(base_score=0.5, booster='gbtree', colsample_bylevel=1,
             colsample_bynode=1, colsample_bytree=1, gamma=0,
             importance_type='gain', learning_rate=0.1, max_delta_step=0,
             max_depth=3, min_child_weight=1, missing=None, n_estimators=100,
             n_jobs=1, nthread=None, objective='reg:squarederror',
             random_state=0, reg_alpha=0, reg_lambda=1, scale_pos_weight=1,
             seed=None, silent=None, subsample=1, tree_method='gpu_hist',
             verbosity=1)
```

以上
文献管理のすすめ

# 最近困ったことがあります
最近困ったことが起こりました．なんとMendeleyのiosアプリとandroidアプリの提供が廃止されました．

それまで行っていた
* Mendeleyで文献管理
* Goodnoteで文献に書き込み
* Google driveで書き込んだ文献を保存

を行っていたのですが，その素敵環境がなくなりました．

その他の環境を求めていた僕にとっては環境を変える転機が来ました．

# Paperpileを使って見よう
Paperpileはchromeの拡張機能として使える文献管理ツールです．
一ヶ月で$3かかるのが少し気になりますが，Endnoteなどは採用していない大学も多く，導入するのに今後のキャリアを考えると少し不安なので，Paperpileを使用することにしました．

さらに追加情報として，最近，Paperpileのiosアプリができました．
これを使えば前の環境を大幅に崩さずに行けるはず

まだ書き途中なので，更新します・・・・(2021/06/03)
Kotlin クラスとインスタンス

##▼クラス
複数の変数などを束ねる場所のこと
関数や配列も入れられる

```kotlin
class A {
    val a = "りんご"
    val b =100 
}
```

##▼インスタンス
インスタンスは変数に数字や文字を入れることではなく、クラスを入れること。
変数などが入っているクラスをコピーして、クラスの中身を使えるようにすること。

クラスの中身を使えるようにするには・・・
インスタンス化し、クラスをコピーする
ここでは、「class A」というのがmain関数の中で変数としてコピーされている。
これはクラスの中身を変更する必要がなく、main関数の中で修正等ができるようになる。

```kotlin
fun main() {
    val a = A()
}
```
↓

```kotlin
class A {
    val a = "りんご"
    val b =100 
}
```
コピーしたクラスは表示させたり、

```kotlin
fun main() {
    val a = A()
    parintln(a.b)
}

///結果
///100
```
編集することが可能になる

```kotlin
fun main() {
    val a = A()
    parintln(a.b)
    
    a.b = 300
    println(a.b)
}

///結果
///100
///300
```

###▼束ねて管理

```kotlin
fun main() {
    var name:String = "みかん"
    var price:Int = 100
    
    println("そらは${name}を${price}円で買った")
}
///そらはみかんを１００円で買った
```

これをクラスとインスタンスを使って作ってみる

```kotlin
fun main() {
   val orange = Fruit()
   orange.p()
}

class Fruit {
    var name:String = "みかん"
    var price:Int = 100

    fun p {
        println("そらは${name}を${price}円で買った")
   }
}
///そらはみかんを１００円で買った
```

編集も可能

```kotlin
fun main() {
   val orange = Fruit()
   orange.price = 200
   orange.p()
}
```
編集することで、100円が200円に変更できる

ただ、１つのものを束ねるだけであれば、変数の方が使いやすい。
クラスやインスタンスで使うのは複数束ねる必要があるときが便利になる。

```kotlin
fun main() {
   val orange = Fruit()
   orange.p()

   val strawberry =Fruit()
   strawberry.name = "いちご"
   strawberry.price = 400
   strawberry.p()
}
```

複数束ねる場合には、上で書いたクラスはいじる必要がなく、インスタンスを増やして同じように書いてあげることで束ねることができる
javaでコーディング中にちょっとした確認したいときにifの代わりにassertを使う

例えば以下のようなケースです。
入門書とかにはしっかり書いてありますが、意外と忘れてたり使ってなかったりします

```java:Main.java
public static void main(String[] args) throws Exception {
	// 構文　assert テスト対象 : 失敗したときのメッセージ
		assert sum(2 ,4) == 6 : "method \"sum\" result is Unexpected. arg[0]: 2, arg[1]: 4";
		assert sum(2 ,5) == 6 : "method \"sum\" result is Unexpected. arg[0]: 2, arg[1]: 5";
}

static int sum(int a, int b){
	return a + b;
}
```

assertが成功した場合何も起こりません。失敗すると以下のように教えてくれます。

```
Exception in thread "main" java.lang.AssertionError: method "sum" result is Unexpected. arg[0]: 2, arg[1]: 5
	at Main.main(Main.java:8)
```

アサーションを有効にするには、実行時のオプションに`-enableassertions`を付けてやる必要があります。
【備忘録】AWS Cloud9を用いたIDE環境構築

#はじめに
Ruby on Railsチュートリアルの環境構築編その１です。
AWS　Cloud9を用いたIDE環境構築の流れをメモしておきます。
今回はAWSにログインし、チュートリアルを実行するためのワークスペースを作成するまでの手順を記録します。

#大まかな流れ
1. AWSのアカウントを作成し、ログインする。<br>
アカウント作成時には、メールアドレスの他に、住所やクレジットカードの情報を入力する必要があります。<br>
アカウント作成後、ルートユーザーでログインします。<br><br>
2. チュートリアルを実行するワークスペースを作成する。<br>
AWSマネジメントコンソールの検索窓に"Cloud9"と入力して検索、Cloud9のサービスを選択する。<br>
Cloud9のトップページの右上の"Create　environment"をクリックする。<br>
以下の箇所を変更する。各stepで該当箇所を変更したら、"Next step"をクリックする。<br>
・step1「Name　environment」のName欄に、ワークスペースの名前をつける。<br>
・step2「Configure settings」のPlatformを”Ubuntu Server １８.04 LTS”を選択する。<br><br>
3. インデントの設定を変更する。<br>
ワークスペースが作成できたら、インデントの設定を変更する。<br>
変更するためには、まずページの右上の歯車マークをクリックして、「Preferences」タブを開く。<br>
その後、タブ内の「Code　Editor」欄のSoft　Tabsの値を「２」に変更する。<br>
※設定の変更はその場で反映されるため、「Save」ボタンをクリックする必要はない。

以上でワークススペースの作成が完了です。

#最後に
次は、クラウド環境にRailsをインストールしていきます。
それでは！
クラスのInitを自動的に作成する



プログラミングをしていて以下のようなモデルクラスを作成した時、Initをいちいち書くのは大変です。
Xcodeが11.4以降の自動で生成することができます。

```swift:
class Product {
    var id          :String
    var name        :String
    var arriveDay   :Date
}
```

手順としては
１：クラス名にカーソルを合わせる
![Screen Shot 2021-06-03 at 12.52.09 AM.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/300780/26e6e35e-64f9-5c52-87d4-19acbcfa0463.png)

２：右クリックでRefactorからGenerate Memberwise Initializerを選択することで自動生成されます。
![Screen Shot 2021-06-03 at 12.57.33 AM.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/300780/922610e1-45ab-f525-e98e-56230a6d8ac2.png)


・ちなみにクラスだけではなく、構造体でも同じことができます。
Gitでcloneしてから自分のブランチを作成するまでの流れ

## 記事を作成した経緯
#### プログラミングの課題管理をする際に、Githubで管理したい！<br>ということで、説明用に記事を作成しました。

## コード

#### ①作業フォルダの作成＆移動
```
$ mkdir workspace && cd workspace
```
#### ② リポジトリをclone
```
$ git clone https://github.com/XXXXX/xxxxxx.git
```
##### ③IDEでcloneしたファイルを開く<br>④ターミナルを開く
#### ⑤現在のブランチを確認
```
// ブランチの確認
$ git branch
//現在のブランチが表示
* master

できない場合は、.gitがあるフォルダの直前まで移動してください。
隠しフォルダは、「⌘+shift+.」で表示できます。
```
#### ⑥ブランチを切り替え（今回はdeveloper)　※masterから切る場合は不要
```
//ブランチの切り替え
$ git checkout developer
// 確認
$ git branch
// master 配下のdeveloperブランチに切り替わった
  master
* developer
```
#### ⑦developerの配下にブランチを切る
```
// developerの配下にブランチ(member1)を作成＆切り替え
// git checkout -b <作りたいブランチ名> <親ブランチ名>
$ git checkout -b member1 develper
// 確認
$ git branch
  master
  developer
* member1 // 作成・切り替わってる
```
#### ⑧リモートとして登録
```
// git push -u origin <ブランチ名＞
$ git push -u origin member1
```
### ⑨完成
Github等確認すると、新しくブランチが作成されていることが確認できます。

###　追記：コードを修正する場合
#####　適当にコードを修正（index.htmlを作るなど）
#### コミット　〜　プッシュまで
```
$ git add -A
$ git commit -m "コメント"
//2度目以降はpushのみ
$ git push

```
[備忘録]Juliaで絵文字プログラミング

Juliaでは変数や関数の名前にUnicode文字を使うことができる。

従って、絵文字も利用することができ、[公式ドキュメント](https://diffeq.sciml.ai/stable/analysis/parameterized_functions/)にも下記の通り利用例が記載されている。

```julia
f = @ode_def begin
  d🐁  = α*🐁  - β*🐁*🐈
  d🐈 = -γ*🐈 + δ*🐁*🐈
end α β γ δ
```

これはLotka-Volterraの方程式と呼ばれる、捕食者(🐈)と被食者(🐁)の個体数の変動を表現する数理モデルである。
このように、変数に絵文字を使うことでコード内の変数の意味の直感的な理解が可能になる。


# SIRモデル
SIRモデルは感染症の基本的な数理モデルであり、**S**usceptible（感染可能者）、**I**nfectious（感染者）、**R**emoved/**R**ecovered（感染後死亡者、もしくは免疫獲得者）の変動を記述する。

```math
\begin{align}

\frac{dS}{dt} &= -\beta SI \\
\frac{dI}{dt} &=  \beta SI -\gamma I \\
\frac{dR}{dt} &=  \gamma I \\

\end{align} 
```

# Plotsによる可視化
このモデルを先ほどのLotka-Volterraの方程式のようにJuliaで計算する。
ここでは感染可能者Sを🌝、感染者Iを🤧、免疫獲得者Rを😷で記述し、Plotsで可視化する。
但し、総人口を1とし、人数ではなく割合で表す。

```julia:SIR_plots.jl
using DifferentialEquations
using Plots

sir_ode = @ode_def SIRModel begin
    d🌝 = -β*🌝*🤧
    d🤧 = β*🌝*🤧-γ*🤧
    d😷 = γ*🤧
    end β γ

parms = [0.1,0.05]
init = [0.99,0.01,0.0]
tspan = (0.0,200.0)
sir_prob = ODEProblem(sir_ode,init,tspan,parms)

sir_sol = solve(sir_prob,saveat = 0.1);

plot(sir_sol,xlabel="Time",ylabel="Number")

savefig("SIR_plots.png")
```

このまま実行すると、以下のように🌝と🤧が文字化けしてしまう。（豆腐◻︎と呼ばれている）
フォントやエンコーディングを変えても豆腐📛のままだった。
![SIR_plots.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/423862/3ada6648-ef52-32d9-9061-36bf5fcc55fe.png)

# Pyplotによる可視化
Pyplotで可視化した場合、以下のようになる。

```julia:SIR.jl
using DifferentialEquations
using PyCall,PyPlot

sir_ode = @ode_def SIRModel begin
    d🌝 = -β*🌝*🤧
    d🤧 = β*🌝*🤧-γ*🤧
    d😷 = γ*🤧
    end β γ

parms = [0.1,0.05]
init = [0.99,0.01,0.0]
tspan = (0.0,200.0)
sir_prob = ODEProblem(sir_ode,init,tspan,parms)

sir_sol = solve(sir_prob,saveat = 0.1);

rc("font", family="Segoe UI Emoji")
plot(sir_sol.t,sir_sol[1,:],lw=1,label="💪😀")
plot(sir_sol.t,sir_sol[2,:],lw=1,label="🦠🤧")
plot(sir_sol.t,sir_sol[3,:],lw=1,label="💉😷")
xlabel("Time")
ylabel("Number")
legend()

savefig("SIR.png")
```

Pyplotで可視化した場合、以下のように凡例に絵文字を使うことができる。
（ただこれはJuliaの恩恵とは言えない気がする😅）

![SIR.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/423862/af6ca536-b00c-4ac1-576c-a23e0d46ebcf.png)

Plotsで絵文字を使う方法や、もっと上手い方法を知っている方がいたら教えて下さい🙏。

# 参考
- [[Julia] UTF-8 表記の演算子たち](https://qiita.com/tenfu2tea/items/c3402e647c49e989ac2f)
- [感染病の数学予測モデル　(SIRモデル）：事例紹介(1)](https://qiita.com/kotai2003/items/d74583b588841e6427a2)
- [GR バックエンドの Plots.jl で日本語かけるでキュ！](https://qiita.com/SatoshiTerasaki/items/441e1e399271994795bb)
- [matplotlib in julia：PyPlotメモ](https://qiita.com/tg-git/items/61b7714665b73b3e4d9a)
sudo 権限での実行ができない時のための備忘録

sudo権限でコマンド実行しようとしたところ怒られたので、備忘録。

初期では使えないらしいです。(exampleは自分のユーザー名に都度書き換えてください)
場合によってはパスワードは聞いてきて入力した上で以下のように拒まれます。自分はそうでした、、
自分から聞いてきてなんやねんて感じでしたが、断る事決めてる癖に聞いてくるとか性格悪いですねw
何かセキュリティ的な観点があるのでしょうか?深追いはしませんが。

以下はルート権限で3306のポート番号は何のアプリケーションが使っているのかのコマンドです。

```
[user@localhost ~]$ sudo lsof -i:3306
user is not in the sudoers file.  This incident will be reported.
```


###visudo

/etc/sudoersにユーザの権限が指定されています。 こちらを編集してユーザに管理者権限を追加します。

まずはルート権限に入ります。 以下ではsu-rootとしてますが、自分はsu - で入れました。
ルートのパスワードを入力します。

```bash
su - root
Password: 
[root@localhost ~]# 
```

続いてvisudoで/etc/sudoersを編集します。

```
visudo
```

皆様おなじみ?のviエディタで編集します。msに権限を全て付与します。(ユーザー名は各々変えて下さい)

```
## The COMMANDS section may have other options added to it.
##
## Allow root to run any commands anywhere
root    ALL=(ALL)       ALL
 m2    ALL=(ALL)       ALL # <- 追加したユーザ
```

毎回sudo権限でパスワード聞かれるのはだるいので以下のように書き換えてください。

```
## The COMMANDS section may have other options added to it.
##
## Allow root to run any commands anywhere
root    ALL=(ALL)       ALL
m2    ALL=(ALL)       NOPASSWD: ALL # パスワードなし sudo の実行
```


試しにsudo権限で先ほどのポート確認
(セキュリティ関連でどこまで隠せばいいかわからないので数字の部分は)

```
$ sudo lsof -i:3306
COMMAND  PID  USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
mysqld  〇〇 mysql   〇〇  IPv6  〇〇      0t0  TCP *:mysql (LISTEN)

```


確認できていますね。
それでは
以下参考にしたサイト

https://www.suzu6.net/posts/144-centos-su-user/
TypeScriptの仮引数は関数内で再代入が行われていない場合暗黙的にconst扱いになるのでType Guardが有効

今まで知らなかったネタをGitHubで見つけたので備忘録として。

元ネタは[こちら](https://github.com/microsoft/TypeScript/pull/10357)。TypeScript 4.3.2で確認しています。

https://github.com/microsoft/TypeScript/pull/10357

JavaScriptのコールバック関数内では、Type Guardによる絞り込みの結果がリセットされます。

```typescript
declare let text: string | undefined;
if (!text) throw new Error();
// エラーじゃない
text.toUpperCase();
setTimeout(() => {
  // @ts-expect-error Object is possibly 'undefined'.
  text.toUpperCase();
}, 0);
```

[上記の例](https://www.typescriptlang.org/play?#code/CYUwxgNghgTiAEEQBd7JAD2QLngZ2RgEsA7Ac3gB94BXE0AM1JGAG4AoIh+ACgEJ0WAJRoAFjAD2Ad3gkQMgKIxJMHkI4B6DfEAVDIEuGQD8MgDQZAwQyArBkAiDO0HIAdMgkBVAA7OQMAMJQ8INRx-IACpEALYgEjTIPGrwALwAfPAA3uzw8FrwAALIeAC0mG5gyPnKEjDwAPIARgBW4KhEePDOEnh4RFUQAJ7wAOR0jMzAvbapaJh2Di5unt6+6uwAvgA08AAMC0A)において、2行目による絞り込みは4行目には有効ですが7行目には有効ではありません。

これは周知の事実かと思いますが、コールバック関数は遅延評価されるため、Type Guardによる絞り込みが行われた後に値が変わってしまる可能性があるからです。

値をconstな変数に代入することで、[この制約を回避](https://www.typescriptlang.org/play?#code/CYUwxgNghgTiAEEQBd7JAD2QLngZ2RgEsA7Ac3gB94BXE0AM1JGAG4AoMAexILU2QAmeAF5+WDkQbwAFAEJ0WQQEo0ACxhcA7vBIgdAURiaYM5RzwoAKkQC2ILjWQyzogHzwA3u3jwA9H7wgBUMgJcMgD8MgBoMgMEMgFYMgCIMPuJCAHTIXACqAA6ZIDAAwlCWZhwAvgA08AAM5uxAA)することができます。

```typescript
declare let text: string | undefined;
const text2 = text;
if (!text2) throw new Error();
setTimeout(() => {
  // エラーじゃない
  text2.toUpperCase();
}, 0);
```

実は、関数の引数においては、[関数内で明示的に再代入を行う文がない限りType Guardの結果が維持](https://www.typescriptlang.org/play?#code/GYVwdgxgLglg9mABFOBVADugpgJwMICGAzlgBRRYAeUA-AFyJFQ4xgDmAlIgN4BQiiGMESkAhBWpccWKCBxgA3P0QB6FYkAVDIEuGQD8MgDQZAwQyArBkAiDMumz5IrgF4AfMipQAdCgzZ8xMhyUBfXkA)されます。

```typescript
function toUpperCase(text?: string) {
  if (!text) return;
  // エラーじゃない
  return () => text.toUpperCase();
}
```

let等変更可能な変数に再代入された場合はこの限りではありません。通常は関数の仮引数に代入なんてしないよね、ということなのでしょう。
【JavaSctipt,TypeScript】論理演算子の基本と応用

## 基本

* どちらの演算子も両方がTrueだったらTrue、FalseだったらFalseになる
* JavaScriptの仕様上判定は左から右へ行われる。

### ||演算子

```main.js
console.log( true || true )  //true
console.log( true || false ) //true
console.log( false || true ) //true
console.log( false || false ) //false
```

* 数学的な意味では「<b>または</b>」 記号であらわすと∪
* a || b　であればaまたはbのどちらかを満たす範囲
* プログラミングであればどちらかがTrueであればTrueになる

![basic-negation-condition-and-or-02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/790448/49971a95-e193-255a-0ba6-a19b29b471ad.png)




### &&演算子
```main.js
console.log( true && true ) //true
console.log( true && false ) //false
console.log( false && true ) //false
console.log( true && false ) //false
```

* 数学的な意味では「<b>かつ</b>」 記号であらわすと∩
* a && b　であればaまたはbの両方を満たす範囲
* プログラミングであれば両方TrueでないとTrueにならない。

![basic-negation-condition-and-or-01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/790448/6eb98e8c-10ff-3d50-d361-95f3842ac7e8.png)


## JavaScriptでの演算子の法則

### ||演算子

* ||の場合、左式が<b>falseもしくはfalseとみなすことができる(falsy)値<b>の場合右式を返す
* これら全て出力は "右式を返すよ" になります。

```main.js
console.log( false || "右式を返すよ")
console.log( 0 || "右式を返すよ")
console.log( null || "右式を返すよ")
console.log( undefined || "右式を返すよ")
console.log( NaN || "右式を返すよ")
console.log( "" || "右式を返すよ")
```

### &&演算子

* &&の場合、左式が<b>trueもしくはtrueとみなすことができる(truthy)値<b>の場合右式を返す
* これら全て出力は "右式を返すよ" になります。

```main.js
console.log( true && "右式を返すよ")
console.log( 1 && "右式を返すよ")
console.log( "左式だよ" && "右式を返すよ")
```

* これらの法則はほかのプログラミング言語でも使用できたりもします。

## JavaScriptでの応用

### Reactでの応用

* ||の左式がtrueの場合右式を返却する仕組みを利用してこのような書き方が出来ます。

```App.jsx
import { useState, useEffect } from 'react';

export const App = () => {
  const [admin , setAdmin] = useState('false')
  
  return(
    <div>
      {admin && <AdminPage />}
    <div>
  )
}
```

①Admin(管理者)かどうか判定するStateを作成
②管理者であればAdminPage(管理者画面)を出力する。
※本来であれば管理者かどうかとかはhook化して汎用的にするのがベスト

## まとめ

### ||演算子
* 左式がfalseとみなすことができる値の場合、右式に設定されている値を返却
* 左式がtrueとみなせる場合はそのまま左式を返却

### &&演算子
* 左式がtrueとみなすことができる値の場合、右式に設定されている値を返却
* 左式がfalseとみなせる場合はそのまま左式を返却


特にフロントエンド開発で上手いこと使いこなせればコードの質が上がりますが、
使いすぎて可読性を落とさないように注意しましょう。
[Xcode / CocoaPods] pods install時に出た警告文(Smart quotes were detected)

## Smart quotes were detected and ignored in your Podfile.


`Podfile`に記入 -> `pods install`
この警告文が出て、一応無事に消すことが出来たので備忘録。


### スマートクォートの検出

#### 警告内容

```
[!] Smart quotes were detected and ignored in your Podfile. 
To avoid issues in the future, you should not use TextEdit for editing it. 
If you are not using TextEdit, you should turn off smart quotes in your editor of choice.
```

#### 直訳

> Podfileにスマートクォートが検出され、無視されました。今後の問題を回避するために、編集にTextEditを使用しないようにしてください。もしTextEditを使用していない場合は、お使いのエディタでスマートクォートをオフにしてください。

#### 解消方法

ファイル中にスマートクオートがあるということ。
とりあえずファイル中のシングルクオートを一つ一つ書き直していった結果・・・

![スクリーンショット 2021-06-02 23 41 41](https://user-images.githubusercontent.com/62790209/120501786-d94fe980-c3fc-11eb-9fe5-a358a49c46d0.png)

このシングルクオートの形がちゃうやんけ！

という事で、打ち直したら警告消えました。

#### ちなみに

原因となった箇所は、Firebase SDKのインストールの時、
公式チュートリアルの`これを追加してね！`なコードをコピペしました。
なんということだ・・・安直なコピペは気をつけないといけないですね。
[Teams] チャネル内のファイル共有禁止

#この記事について
Teams は Microsoft 365 グループをベースに構成されている。
どういうことか？というと、従来 (オンプレミス時代) は、各サービスに対してユーザーやグループに権限を与えて利用していた。
Office 365 は協業ありきの考え方なので、グループに紐づく形で色んなサービス (製品) が用意されている。
Teams が特に顕著で、Teams でチームを作成すると、その作成したチームに対して Microsoft 365 グループが作成される。
そして、その Microsoft 365 グループに紐づく形で SharePoint Online のサイトと Exchange Online のグループ メールボックスも作成される。
メンバー内ではみな同じ目的で集まっていること前提なので同じ共有権限でリソースにアクセスできるようになる。

#チーム内でファイル共有を無効にする
チーム内 (チャネル内も同じ) でのファイル共有は Microsoft 365 グループに紐づいた SharePoint Online が利用される。
なので、Share Point のサイトで権限をはく奪することで、ファイル共有を無効にできる。(チャットや会議は継続して利用可能)

####1. Teams から対象のチームにアクセスして [ファイル] タブから "SharePoint Online で開く" をクリック。
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/ccc5772a-c68a-f2f8-36ef-940f7d0665af.png)


####2. 開いた　SharePoint の画面右上にある歯車をクリックして "サイトのアクセス許可" をクリック。
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/ce48a18b-116d-eb4a-4454-830663b53c78.png)


####3. "高度なアクセス許可の設定" をクリック。
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/d75c8f22-84e5-05a9-6e0a-401d694782d6.png)


####4. "メンバー" または "閲覧者" (もしくは両方) をクリックし、含まれているグループが選択された状態で [操作] から "グループからのユーザーの削除" をクリック。
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/f69a9b05-cdf5-bf1f-fb18-401b928309f6.png)
-
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/313a3784-b140-9d85-5b59-389a0cf87d60.png)

これで、対象チームの所有者以外は SharePoint にアクセスできなくなったので、ファイル共有ができなくなり Teams 上で [ファイル] タブをクリックすると以下のように権限不足のエラーが表示されるようになる。
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/6b595634-efc6-43db-834c-29fe677e6c87.png)

もし、チームオーナーもアクセス不可とする場合は同様に Share Point 側で権限をはく奪すればよい。
誰も管理できなくなると不便なので、管理者などにサイト管理者の権限を付与することを忘れずに。
あとは、もしチーム作成をIT 部門で請負とかせず、ある程度自由にユーザーに作成させている場合は、チームの作成者 (チームオーナー) には権限を付与したままの方が融通が利きやすいだろう。
例えば以下のようにメンバーを所有者に変更することで、一時的にファイル共有可能にしたりとかも可能。
>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1307699/85a0c482-9186-2c50-31c0-61707c50bb9f.png)
輪読メモ｜JavaScript｜オブジェクトと配列におけるdelete演算子の結果

[開眼！ JavaScript――言語仕様から学ぶJavaScriptの本質](https://www.oreilly.co.jp/books/9784873116211/)を輪読会で読み進めている最中です。

本書の中で紹介されていたdelete演算子について、Chromeのデベロッパーコンソールを利用して復習・確認した📝になります。

#### オブジェクトと配列に対してdelete演算子を利用する
##### オブジェクトの場合
```js
const obj = {1:1, 2:2, 3:3, 4:4};
console.log(obj);  // {1: 1, 2: 2, 3: 3, 4: 4}

delete obj['2'];  // true
console.log(obj);  // {1: 1, 3: 3, 4: 4}
console.log(obj[2]);  // undefined

const obj2 = {test: 'aaa'};
console.log(obj2);  // {test: 'aaa'}
obj2[test] = undefined;
console.log(obj2);  // {test: undefined}
obj2[test] = null;
console.log(obj2);  // {test: null}
```
delete演算子はオブジェクトからプロパティの存在を削除する唯一の方法。
プロパティの値に`undefined`や`null`を設定しても、プロパティ値を変更することにすぎない。削除するにはdelete演算子を利用する必要がある。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/536171/ee56fe47-4314-794d-a72f-e8fed40b9ab7.png)


##### 配列の場合
```js
const ary = [1,2,3,4,5];
console.log(ary);  // (5) [1, 2, 3, 4, 5]

delete ary[2];  // true
console.log(ary);  // (5) [1, 2, empty, 4, 5]
console.log(ary[2]);  // undefined

console.log(ary.length); // 5
delete ary.length;  // false
console.log(ary.length); // 5
```
配列の削除も可能だが、配列の指定要素は`undefined`になり、`length`は維持される。
プロトタイプチェーンで継承するプロパティは削除できない。

##### 2次元配列の場合
```js
const ary_two = [[1,2,3,4],[5,6,7,8]];
console.log(ary_two); // (2) [Array(4), Array(4)]

delete ary_two[1][2] // true
console.log(ary_two); // (2) [Array(4), Array(4)]
/*
(2) [Array(4), Array(4)]
  0: (4) [1, 2, 3, 4]
  1: (4) [5, 6, empty, 8]
*/

delete ary_two[1] // true
console.log(ary_two); // (2) [Array(4), empty]
/*
(2) [Array(4), empty]
  0: (4) [1, 2, 3, 4]
*/
```
2次元配列も配列と同様入れ物としての長さは元のまま残ってしまう。

##### 配列とオブジェクトの組み合わせ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/536171/2b157671-9cc7-d530-4f6a-340876f0a10f.png)
オブジェクトのプロパティであれば削除可能だが、配列の場合は通常の配列と同様に入れ物の形は残ってしまう。

* * *

現時点で`delete`演算子を利用する機会が無かったために、現環境における運用のイメージは湧いていないが、配列とオブジェクトで`delete`演算子を利用した場合の結果が異なることを理解することができた。
自作クラスをMapのkeyにする時の注意点

# エラーで詰まった所
JavaでHashMapを用いる際に、自作クラスをkeyとしてなにかしらの値を持つ。という実装を行っていました。
それらを利用し、HashMapのcontainsKeyメソッドでkeyである自作クラスが含まれていれば特定の処理をするといった条件分岐をしていました。
ですが、思っていた挙動通りに動かず、エラーも出ていない為、悩んでいました。
Javaを始めて経験が浅かったものの、HashMapの内部の動きを理解せず使用していたので、今回この記事を通して学んだことを記しておきます。
# HashMapの内部の動き
HashMapの内部は配列で実現されており、ハッシュテーブルを保持しています。
keyとvalueをputすることでkeyをハッシュ関数に通し、それをインデックスとしてvalueと一緒に格納されます。
値をgetする場合はkeyをハッシュ関数に通し、配列のインデックスの値としてvalueを取り出していくそうです。
keyのハッシュコードが一致するかどうかを判断し、そのあとにget(key)で指定したkeyがequalsで一致すればvalueを取得できます。
ハッシュコードが一致するかどうかを確認するのは、オブジェクトが同じならハッシュコードも同じという前提があるからですね。
なので**equalsとhashCodeを正しくオーバーライドする**ことが重要なのですね。
クラスを作成する時になんとなくこれら2つのメソッドをEclipseで自動生成していたので、これらの重要性を理解していませんでした。
JavaSilverの学習も行っていたので、黒本の中でequalsやクラスの同値性・同一性についてが詳しく解説されており、この問題に気づくことができました。
#具体的な実装
jspとServletのみで疑似ECサイトを作成しており、カート機能を作成していて、商品であるitemクラスをkeyに、カートに入っている個数を持っているという実装です。

```java:itemBean
import java.io.Serializable;

public class ItemBean implements Serializable {
	private int item_id;
	private String name;
	//~~~~~~~~~~~~~~

	public int getItem_id() {
		return item_id;
	}

	public void setItem_id(int item_id) {
		this.item_id = item_id;
	}
         
        public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}


	//~~~~~~~~~~~~~~~~~~~~

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result + item_id;
		result = prime * result + ((name == null) ? 0 : name.hashCode());
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (!(obj instanceof ItemBean)) {
			return false;
		}
		ItemBean item = (ItemBean)obj;
		if (item.getItem_id() == this.getItem_id() && item.getName() == this.getName) {
			return true;
		}
		return false;
	}
```
一意なデータであるitem_idを元にequalsをオーバーライドしました。
これらをオーバーライドすることでcontainsKeyを使用する際にオーバーライドしたhashcodeとequalsが使われ期待した通りの動きができました。これらを実装していないとObjectのhashcodeとequalsが使用されるので、期待通りの挙動にならなかったわけですね。

```java:beginersugi
//オーバライドしている時
cart.getCartMap().containsKey(item) //true
//オーバライドしていない時
cart.getCartMap().containsKey(item) //itemクラスでは無く、Objectクラスのequalsが使われる為false
```

#まとめ
以上、初心者にはありがちなミスだそうですが、便利なメソッドも内部の動きを理解した上で使用していきたいですね。
これを調べるにあたって性能の為にComparableを実装しておく。みたいな記事を見かけたのでそちらも、理解しておこうとおもいます。
rails seedとは、　備忘録

<h2>seeds.rbとは</h2>
アプリなどでデータベースに初期データを登録したり、
テストデータなどを登録してくれるファイルのこと。


<h2>seed ファイルの使い方</h2>
<h3>1件づつデータを入れる場合</h3>
<pre>モデル名.create(カラム1: 値1, カラム名2: 値2, カラム名3: 値3 …)</pre>

＊日本語を使用する場合はファイルの先頭に「# coding: utf-8」と指定する必要があり？

入力したい初期データをseeds.rbに入力したら、保存して下記コマンドを入力すると反映される。

<pre>rails db:seed</pre>

rails console(rails c)を開いて、
<pre>モデル名.all</pre>

でデータベースの中身を確認できる。


<h3>複数件データを入れる場合</h3>

<pre>5.times do |no|
  Title.create(:カラム => "値 #{no}")
end</pre>

rubyのfor文を使って複数のユーザーを作っていくやり方。


dbの特定のカラムにuniqueバリデーション（同じカラム内に同じデータは存在できない（user、emailなど））がかけていることが多いと思うので、"値#{n + 1}",など変数を上手く活用してテウとデータなどを作成。



<h3>CSVからインポート</h3>
エクセルでも、テキストエディタからでも、スプレッドシートからでもCSV形式で出力。

<pre>require "csv"
 
CSV.foreach('db/ファイル名') do |info|
  モデル名.create(:カラム1 => info[0], :カラム2 => info[1])
end</pre>


seeds.rbの変更が終わったら保存して、rails db:seedを実行する


<h2>参考サイト</h2>
https://railsdoc.com/page/rake_db_seed

https://qiita.com/ren0826jam/items/b589171502df87e40234

https://qiita.com/takehanKosuke/items/79a66751fe95010ea5ee#:~:text=seed%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%81%A3%E3%81%A6%E4%BD%95,%E5%BF%85%E8%A6%81%E3%81%8C%E5%87%BA%E3%81%A6%E3%81%8D%E3%81%BE%E3%81%99%E3%80%82

https://qiita.com/mmmasuke/items/545afaf5876d3dc52670

https://freesworder.net/rails-seed/