OmniAICreator/Qiita-1.07M huggingface dataset:
ポートの開放することなく、Respberry Piに外からアクセスする(2020年 AWS編)

2017年に書いた[ポートの開放することなく、Respberry Piに外からアクセスする](https://qiita.com/moritalous/items/6ddd36f895ca656eac80)の第2弾です。

自宅に設置したRaspberry Piに外出先からアクセスしたいことってありますよね。
でも、そのためだけにルーターのポートを解放するのも、セキュリティが心配。

今回はAWS Systems Manager Session Managerを使う方法をご紹介します。
SSHもVNCもポートの開放も不要ですよ！

# AWS Systems Manager Session Managerとは

公式サイトによると

> Session Manager はフルマネージド型 AWS Systems Manager 機能であり、インタラクティブなワンクリックブラウザベースのシェルや AWS CLI を介して Amazon EC2 インスタンス、オンプレミスインスタンス、および仮想マシン (VM) を管理できます。

https://docs.aws.amazon.com/ja_jp/systems-manager/latest/userguide/session-manager.html

基本的にはEC2へのログインに使うと便利なものですが、実はSystems Managerはオンプレ環境でも使用でき、Session Manager機能もEC2でなくても利用できるのです。

# 導入手順

以下、手順を追って説明します。

## IAMサービスロールを作成する

IAMロールを作成します。

| 項目 | 内容 |
| --- | --- |
| 名称 | SSMServiceRole(任意の名前) | 
| ポリシー | AmazonSSMManagedInstanceCore(AWS 管理ポリシー) |
| 信頼関係 | ssm.amazonaws.com |

https://docs.aws.amazon.com/ja_jp/systems-manager/latest/userguide/sysman-service-role.html

## アクティベーションを作成する

Raspberry PiにSSMエージェントをインストールする際に必要なアクティベーションキーを作成します。

マネジメントコンソールの`ハイブリッドアクティベーション`メニューから作成します。

| 項目 | 内容 | 
|--- | --- |
| インスタンス制限|1(任意の数)|
| IAM ロール | SSMServiceRole(上の手順で作ったもの) |
| デフォルトのインスタンス名 | Raspberry Pi(任意の名前) |

作成したあと、画面上に`アクティベーションコード`と`アクティベーションID`が表示されるのでメモしておきます。

https://docs.aws.amazon.com/ja_jp/systems-manager/latest/userguide/sysman-managed-instance-activation.html

## SSMエージェントをインストールする
ここはRaspberry Pi上での作業となります。

```console
mkdir /tmp/ssm
sudo curl https://s3.amazonaws.com/ec2-downloads-windows/SSMAgent/latest/debian_arm/amazon-ssm-agent.deb -o /tmp/ssm/amazon-ssm-agent.deb
sudo dpkg -i /tmp/ssm/amazon-ssm-agent.deb
sudo service amazon-ssm-agent stop
sudo amazon-ssm-agent -register -code "[activation-code]" -id "[activation-id]" -region "ap-northeast-1" 
sudo service amazon-ssm-agent restart
```

`[activation-code]`と`[activation-id]`は前の手順でメモしたものを使用します。

https://docs.aws.amazon.com/ja_jp/systems-manager/latest/userguide/sysman-install-managed-linux.html

これで設定は完了です。
設置が完了すると、Session ManagerのマネージドインスタンスのところにRaspberry Piが追加されます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/41574/e50b810e-1870-7a0a-fdda-c82c1639ce15.png)

# 接続手順

Session Managerのマネージドインスタンスのところでインスタンスを選択し、`アクション` -> `Start Session`を選択すると、ブラウザ上でターミナルの画面が表示されます。

これ、ブラウザの画面です。すごいですね。`su - pi`とすることで`pi`ユーザーへの切り替えもできます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/41574/ad3563a9-7207-2522-7d08-1e607589b297.png)

これでいつでもどこでもRaspberry Piと一緒です。
SSHもVNCも不要です。すごいですね。
Rails カスタムHelperでコードを簡略化しよう

# 今日の目標
Railsで美しく見やすいコードを書くためによく使われる「カスタムHelper」というものを紹介していきます。

## Helperとは

「Helper」とは、Viewをよりシンプルに書くためのモジュールです。

Viewでの共通する処理をメソッドとして定義し、簡単に使いまわせるようにした機能です。

Helperを利用することによって、繰り返し記述するような処理を簡略化することができ、開発効率を高めてくれます。

以下のコードはリンクを生成するHelperです。

```
<%= link_to "New User", new_user_path %>
```

Railsにはその他にも、ボタンやフォーム等を作成するためのHelperが多数デフォルトで用意されており、また、Helperを自作することもできます。

Helperを上手く利用することによって、コードを簡略化でき可読性が高まります。

## Helperの作成

実際にHelperを作成します。
Helperモジュールはapp/helpers配下に用意されています。

application_helper.rbには、アプリケーション全体に渡って使用するHelperメソッドを定義し、

user_helper.rbは、user配下のみで使用するHelperを定義します。

user_helper.rbに以下のようなサンプルメソッドを作成します。

```ruby:user_helper.rb
module UsersHelper
  def higakin
    "ひがきHelperサンプル"
  end
end
```
Viewを表示する画面で以下のようにコードを記述すると、helperのtogaminメソッドが呼び出され実行されます。

```
<%= higakin %>
```

[![Image from Gyazo](https://i.gyazo.com/98aaceb2421a458f94d8a508843d3bca.png)](https://gyazo.com/98aaceb2421a458f94d8a508843d3bca)

「ひがきHelperサンプル」という文字列が表示されました。

実際にこのHelperを利用して　プロフィールavaterの表示を行なっていきます。

今回使用するのは　
[![Image from Gyazo](https://i.gyazo.com/4f8d37cedaeb4221babbfae7d28bed6f.png)](https://gyazo.com/4f8d37cedaeb4221babbfae7d28bed6f)画像を登録しない場合デフォルトはこのアイコンになります。よく見るやつです。

[Gravater](https://ja.gravatar.com/)　世界共通のアバターとして認識されている「Gravatar」をユーザープロファイルに導入します。（Gravatarアカウントを作成する必要はありません。Gravatarは無料のサービスで、プロファイル写真をアップロードして、指定したメールアドレスと関連付けることができます。）

```ruby:helpers/application_helper.rb
module ApplicationHelper
  def avatar_url(user)
    return user.profile_photo unless user.profile_photo.nil?
    gravatar_id = Digest::MD5::hexdigest(user.email).downcase
    "https://www.gravatar.com/avatar/#{gravatar_id}.jpg"
  end
end
```
このように　helperで定義した`avatar_url(user)`はユーザーテーブルの中で使い回すことが出来ます。
下記のように　ビューで簡単に呼び出すことが出来ます。


```erb:show.html.erb
<%= image_tag avatar_url(@user), class: "round-img" %>
    
```
変数のように呼び出すことが出来、大変便利です。

[![Image from Gyazo](https://i.gyazo.com/209635b83d2d798a62ce3fa194af5553.png)](https://gyazo.com/209635b83d2d798a62ce3fa194af5553)

今回ヘルパーでメソッドを定義することにより　ビューファイルの記述を短くすることが出来ました。

# 1点注意事項
ただし、1点だけ、定義するファイルだけは注意しなければいけません。


helperを定義するのは、「app/helpers/」ディレクトリに格納されているファイルでなければいけません。

今回の場合は「user_helper.rb」ファイルを作成し、userモデルだけで使用するhelperであれば、このファイルに定義することになります。

コードの可読性を上げ、シンプルなコードを書くことを心がけることで様々な機能の実装が可能になるはずです。
Swift UITableViewの編集モードでのセル並び替え機能

canMoveRowAtを呼び、trueにする。

```swift:sample.swift 
override func tableView(_ tableView: UITableView, canMoveRowAt indexPath: IndexPath) -> Bool {
        return true
    }
```
moveRowAtクラスに並び替えの細かい操作を記入する。

``` swift:sample.swift
override func tableView(_ tableView: UITableView, moveRowAt sourceIndexPath: IndexPath, to destinationIndexPath: IndexPath) {
     //並び替え中に他に行いたい操作を書く(データの保存など)
        }
```


上の２つのクラスどちらも呼び出さないと並び替えをすることは可能にならない。
canEditRowクラスを呼び出さなくても編集モード中に並び替えだけは可能になる。
jQueryのappendで取得元が消えてしまうときの回避方法

# はじめに
エレメントから要素を取得して、その要素を別の場所にコピーする処理をjQueryのappendでしようとしていたのですが、取得元が消えてしまいハマってしまったので、その回避策のメモです。

# 事象
以下のような画面があったとして、「テストタイトル1」をクリックすると、「テストタイトル2」の下に「テスト内容」がコピーされるプログラムを作成したかったとします。

```
テストタイトル1 // ① クリック
テスト内容
テストタイトル2 // ② この下に「テスト内容」がコピーされる
```

そこで、以下のようなHTMLとJavascriptを実装します。

```html
<html>
  <head>
    <meta charset="utf-8">
    <title>テスト</title>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
  </head>
  <body>
  <div id="test" class="test">
    <div class="test-title-1">
      テストタイトル1
      <div class="test-contents">テスト内容</div>
    </div>
    <div class="test-title-2">
      テストタイトル2
    </div>
  </div>
  </body>
  <script>
    $('.test-title-1').on('click', function(){
      const target = event.currentTarget; // クリックした要素(test-title-1)を取得
      const testContents = $(target).find('.test-contents'); // test-contentsクラスの要素取得
      $('.test-title-2').append(testContents); // test-title-2クラスへappend
    });
  </script>
</html>
```

すると、なぜか結果は以下のようになり、「テストタイトル1」直下のテスト内容が消えてしまいます。

```
テストタイトル1
テストタイトル2
テスト内容
```

# 原因
jQueryオブジェクトのappend()は**追加or移動**という仕様でした。

<a href="https://api.jquery.com/append/" target="_blank">公式サイト</a>を見ると、以下のように記載がありました。

> If an element selected this way is inserted into a single location elsewhere in the DOM, it will be moved into the target (not cloned)
(日本語訳)
「この方法で選択された要素がDOMの他の場所の単一の場所に挿入された場合、それはターゲットに移動されます」

つまり、取得したDOMはappendすると、別の要素へ移動されてしまうのです。。。

# 回避策
これを回避するには、**appendする時に、変数を複製すればOK**です。

先ほどのサンプルプログラムを利用すると、具体的には、**clone()メソッド**を以下のように使います。

```html
<html>
  <head>
    <meta charset="utf-8">
    <title>テスト</title>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
  </head>
  <body>
  <div id="test" class="test">
    <div class="test-title-1">
      テストタイトル1
      <div class="test-contents">テスト内容</div>
    </div>
    <div class="test-title-2">
      テストタイトル2
    </div>
  </div>
  </body>
  <script>
    $('.test-title-1').on('click', function(){
      const target = event.currentTarget;
      const testContents = $(target).find('.test-contents').clone(); // ここにclone()を追加
      $('.test-title-2').append(testContents);
    });
  </script>
</html>
```

すると、取得した要素は一度クローン(複製)されるため、appendが移動するのは複製した要素となるので、以下のように正常にコピーできます。

```
テストタイトル1 // ① クリック
テスト内容
テストタイトル2
テスト内容 // ② テスト内容が正常にコピーされる
```
# さいごに
2020年から個人ブログはじめました！

フリーランスエンジニアになって得た知識と経験をもとに、フリーランスエンジニアに関する情報をはじめ、IT技術情報や業界情報、エンジニアライフハック等のコンテンツを配信していく予定です。

まだまだ記事数は少ないのですが、週単位で更新してますので、もしご興味ございましたら、みていただけると嬉しいです。

https://yacchi-engineer.com/

さいごまでお読みいただき、ありがとうございました。
IT崩壊を防ぐ４つの提言

#IT崩壊を防ぐ４つの提言
某ウィルスと違って検査がありませんし、滅多なことでは報道もされないのですが
闇は深いように思われます。勇気を振り絞って防ぐための提言をしたいと思います。
##ピラミッド構造を見直す。
疑問：なんでJavaの案件なのに、コボラーの方々が設計書を書いているのでしょうか？
なんで詳細設計書のレビューをコボラーがやってるんでしょうか？
アンサー：巨大企業の偉い人達って設計者ですら見えてないのじゃないでしょうか？下々がどっかにいてよろしくやってくれるとしか思ってないのかも。
実作業者にフォーカスが当たるようにピラミッド構造を見直しましょう。
実作業者をやたらと管理したがる体質というのも改善が必要だと思われます。
大企業じゃないから、若いから善ということもないので、一人でも下の人間が入ってきたら
やたら管理したがる体質というのをどうにかしないとシステム自体が息ができなくなってしまいます。
##レビューアーよりリーダーを
レビュー主体で管理していくよりまず、リーダーさんが道を切り開いていくHowを強力にリードしていくべきです。

##ラインリーダー・ラインマネージャーの考え方を導入
今動いているラインのリーダーさんが一番力を持つべきだと思います。
○○プロジェクト○○案件の長ぐらいでしょうか？
その上がいたにしても人のアサインなどは○○プロジェクト○○案件のリーダーさんが
責任を持つべきだと思います。

##設計書・人
フレームワークっていう存在も出てきたため、フレームワークに対する無知がバグの発信源になっていることを
噛み締めていただきたいと思います。設計をフレームワークに肩代わりしてもらっていることを安易に考えないことだと思います。←　早い段階でのセッションタイムアウトやセキュリティテストなどテストも工夫が必要かと思われます。
設計すべきでない人が設計をし、プログラムすべきでない人がプログラムをし、いろんな人がたらい回しにして
というクフ王の墓と同じ工数のようなプロジェクトもあったんですがそうなっていないか常に振り返ることは必要かと思います。
来てくれた人を最大限に生かすって結構難しいのでその部分も考えて欲しいと思います。
Ruby 基礎知識

# Ruby基礎知識

#### to_sメソッド
オブジェクトの内容を文字列化するメソッド

```ruby:ruby

puts 1.to_s + 7.to_s #=> "17"

puts 'nil'.to_s #=> ""
```
<br>

#### to_iメソッド
文字列表記から整数表記へ変換するメソッド

```ruby:ruby
str = "23"
puts str.to_i + 12  #=> 35
```
<br>

#### to_fメソッド
整数表記から小数表記へ変換するメソッド

```ruby:ruby
n = 5
puts n.to_f       #=>5.0
puts n.to_f / 2   #=>2.5
```
<br>

#### メソッドの呼び出し
オブジェクト.メソッド(引数)
*()は省略可


```ruby:ruby
#数値を16進数の文字列に変換

puts 14.to_s(16) #=> "e"

puts 14.to_s 16 #=> "e"
```
<br>


####コメントの入れ方

```ruby:ruby
# 1行の場合（文の途中からでも可）

=begin
複数行
コメント
可
=end
```
<br>

####文字列に変数を組み込む

```ruby:ruby
age = 24
puts "私の年齢は" + age + "歳です" 　　　#=>エラー
puts "私の年齢は #{age} 歳です"　  　 　 #=>私の年齢は24歳です
puts "私の年齢は" + age.to_s + "歳です" #=>私の年齢は24歳です
```
<br>



#### sprintfメソッド


```ruby:ruby
sprintf('%0.3.f', 1.2)  #=> "1.200"
```
チーム開発（デプロイ作業）

前日paysテーブルが存在している為エラーが起きていた。
ローカルのDB
https://gyazo.com/90f323f78f99acc698346026e06a2f54
ロールバックできなかった時参考サイト
https://www.uosansatox.biz/entry/2017/09/08/171851
https://gyazo.com/292d53c7c4aaa0eaaefc53aee5912567

https://gyazo.com/ddf52fb96710ea3ea071fff703bf0697
本番環境のDBをリセットすることで解決
参考サイト
https://qiita.com/potterqaz/items/ea6db5c5be2be389c0bb

デプロイしたら新規登録ができなくなった
https://gyazo.com/8efa041809cc6b8a94c3892e9a262290
ローカルでDBリセット
rails db:migrate:reset
rails db:reset
解決
本番環境でDBリセット
rails db:migrate:reset RAILS_ENV=production
rails db:reset  RAILS_ENV=production
sudo rails db:migrate:reset RAILS_ENV=production
sudo rails db:reset  RAILS_ENV=production
ではでき
参考サイトで
https://qiita.com/potterqaz/items/ea6db5c5be2be389c0bb
解決
Animation Rigging で 握手モーションをろくろ回しモーションに作り変える

Unityの公式動画で[プロシージャルモーションを作る動画](https://youtu.be/saOHaHKSOi0)が配信されていたので試してみました。
![gif_animation_001.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/eb535971-907b-ea0a-a32e-c50f9c7a5bbe.gif)

右下が元のアニメーション、中央が新しく作ったモーションになります。
腰に[Muluti-Parent Constraint](https://youtu.be/saOHaHKSOi0?t=123)を、
両手に[Two Bone IK Constraint](https://youtu.be/saOHaHKSOi0?t=214)を使用しました。
ろくろアニメーション部分は、ベースとなるろくろピボットオブジェクト上に手のコントロールポイントピボットオブジェクトを置き、ろくろピボットオブジェクトをY,Zで適当に回しています。
![gif_animation_002.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/910ef469-eba7-7b62-b413-27bf88a73641.gif)
手の部分にも元のアニメーションを若干残すため、Weightを１より小さくしました。
![2020-04-03_195646.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/dfe682e6-bacd-d5cd-d9da-aa41c49c06fc.png)


動画の通りに両手のコントロールポイントを作成し、それをそのままろくろピボットオブジェクト上にのせてみたのですが、それではコントロールポイントがついてきてくれなかったため、ろくろピボットオブジェクトにスクリプトをアタッチし、手のコントロールポイントをピボットオブジェクトに追随させるようにしました。

```
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

namespace RokuroHand
{
    [System.Serializable]
    public class RokuroHandInfo{
        public Transform pivotTr;
        public Transform targetTr;
        public bool disablePosition;
    };

    public class RokuroHandCtrl : MonoBehaviour
    {
        [SerializeField] AnimationCurve m_acY=null;
        [SerializeField] AnimationCurve m_acZ = null;
        [SerializeField] RokuroHandInfo[] m_infoArr=null;
        float m_timer;

        // Start is called before the first frame update
        void Start()
        {
            m_timer = 0f;
        }

        // Update is called once per frame
        void Update()
        {
            m_timer += Time.deltaTime;
            float ty = m_acY.Evaluate((m_timer * 0.25f) %1f);
            float tz = m_acZ.Evaluate((m_timer * 0.33f) % 1f);
            transform.rotation = Quaternion.Euler(0f, ty * 200f, tz * 400f);

            foreach (RokuroHandInfo info in m_infoArr){
				if (!info.disablePosition){
                    info.targetTr.position = info.pivotTr.position;
                }
                info.targetTr.rotation = info.pivotTr.rotation;
            }
        }
    }
}
```

![2020-04-03_200147.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/fe61bd18-edcb-133a-50f0-a0355b3c8637.png)

また、ろくろを回す際にIK制御の左腕が体にめり込んでいたのですが、空のオブジェクトを作成しHINTのところに入れ、適当なPositionを入れることでめり込まなくなりました。
![2020-04-03_200627.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/9664ae96-08a5-334a-2c74-00c82a92963f.png)
![2020-04-03_195646.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/b66b4381-bfeb-c987-bd90-0bf57dfee25d.png)

他にもいろいろなプロシージャルモーションの例があるので、見てみると楽しいかと思います。
![2020-04-03_201335.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/14273eb5-6474-8ca2-4ddd-5bd8d6b327dc.png)
![2020-04-03_201541.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/9534800f-2582-adba-d587-f1106a36e380.png)
【VScode】なぜか自動保存できねえ時の解決法、そしてパーミッション関連のことも【備忘録】

# 【VScode】なぜか自動保存できねえ時の解決法
設定でAfterdelayなどにしてファイルの自動保存機能をつけているVScodeで開発しているときに、
以下のようなエラーが出て、自動が保存ができないような事態の解決法を紹介します
![エラー１.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/411851/a9053cfd-8522-1018-9c97-13f684b85d7e.jpeg)

[アクセス権限が不十分です。[Sudo 権限で再試行]を選択してスーパーユーザーとして再試行してください。]
と出ております。
つまり、現在、Sudoユーザーとして、ファイルにアクセスできていない状態なので、
・スーパーユーザーにモードを変える
・ファイル、あるいはフォルダのアクセス権限（パーミッション）を変更する
方法があります。

今回は後者の手段を用いて、このエラーを解決します。

```:terminal
sudo chmod -R 777 ファイルのディレクトリ位置（Ex.　/Users/kazuhitoNakayama/Desktop/index.html.erb）
```
この一行で、全てのユーザーに対してのファイルの実行権限を与えられるので、
上記エラーが解決されます。

# 解説

## chmodとは
👉ファイルやディレクトリのアクセス権限を変更する際に使うコマンドです
　（UNIX系のOSで使用できます。Ex.Macなど）

使い方は、chmod [オプション] [与える権限] [対象のファイル、ディレクトリのディレクトリ位置]

オプションは私は普段 「-R」を使ってますが、他にもたくさんあるので
「chmod オプション」とかでお調べください！

## 777とは
👉先ほどchmod [オプション] [与える権限] [対象のファイル、ディレクトリのディレクトリ位置]
とお伝えしました。
ここでの[与える権限]について説明すると、アクセス権の記法には２種類あり、
・アルファベット
・数字
があります。

### アルファベットでの記法
あるフォルダの中に入って「ls -l」をすることで、各ファイルの権限を参照できるので、みてみると、
アルファベットの羅列が見えます。

```:terminal
$ ls -l
drwxr-xr-x  2 user_name  group  68  8 30 15:53 css
-rw-r--r--  1 user_name  group   0  8 30 15:53 index.html

```

それぞれの文字は
r:(read)読み込み権限
w:(write)書き込み権限
x:(execute)実行権限
こんな風に対応しております。

例えば上の、drwxr-xr-xをいかに読むかというと
d/rwx/r-x/r-x　
↑こんな風に区切られます。

また、それぞれの区切りの中で、
ディレクトリなのかファイルなのか/所有者に対する権限/グループに対する権限/その他の者に対する権限/
という風に区切られており、それぞれの対象に対して、権限をr・w・xで与えます。
（1文字目に関してはdならば当該ファイルはディレクトリとわかります。-ならばファイルです。）

よって、
d/rwx/r-x/r-xは
ーディレクトリであり
ー**自分**に対して、読み込み、書き込み、実行の全ての権限が与えられており、
ー**グループ**に対して、読み込み、実行権限が与えられており、
ー**その他の者**に対して、読み込み、実行権限が与えられています。


### 数字の記法
シンプルで、上記、r・w・xがそれぞれ数字に変わるだけですね！

r(読み込み権限):4
w(書き込み権限):2
x(実行権限):1

そして今回は３つの数字で権限対象、与える権限を表現します
例えば、731

１つ目の数字：所有者
2つ目の数字：グループ
3つ目の数字：その他の者
という風になっているので、

731は、
所有者は、7=4+2+1なので読み込み、書き込み、実行権限が与えられ、
グループは、3=2+1なので書き込み、実行権限が与えられ、
その他の者は、1なので実行権限が与えられます。

# 総括
冒頭の振り返りで行くと

```:terminal
sudo chmod -R 777 ファイルのディレクトリ位置（Ex.　/Users/kazuhitoNakayama/Desktop/index.html.erb）
```
これによりindex.html.erbのファイルのパーミッションを、誰でも実行できるようにしたので、自分がファイルを変更してもパーミッションで怒られることがなくなったのです！

パーミッションは自分的に忘れやすい！
必覚！
C言語　ALDS1_3_B　Queue

##問題
http://judge.u-aizu.ac.jp/onlinejudge/description.jsp?id=ALDS1_3_B&lang=ja

##要点
**キュー（queue）**あるいは**待ち行列**はコンピュータの基本的な**データ構造**の一つ。 データを先入れ先出しのリスト構造で保持するものである。 キューからデータを取り出すときには、先に入れられたデータから順に取り出される。 キューにデータを入れることをエンキュー、取り出すことをデキューという。

つまり、ところてん方式

ラウンドロビン[^1]スケジューリングは、プロセスを格納（管理）するキューを用いてシミュレートすることができる。まず、初期状態のプロセスを順番にキューに入れる。次にキューが空になるまで、「先頭からプロセスを取り出し、最大でもクオンタム[^2]だけ処理を行い、まだ必要な処理（時間）が残っている場合は再度キューに追加する」処理を繰り返す。


[^1]: ラウンドロビンとは、英語でRound Robinと書きます。 何かの役割や出番を一定条件のもとで順番に交換して実施していくことを意味することばです。 特に頭を使うことなく、単純だけど平等に永遠と行える方法でパソコンのOSのタスク管理など、さまざまなところで採用されています。

[^2]: CPUが処理できるプロセスの最大q msのこと。一度に処理できる範囲のこと。

###キューの操作

- enqueue(x)
    - キューの末尾に要素xを追加する。
- dequeue()
    - キューの先頭から要素を取り出す。
- isEmpty()
    - キューが空かどうか調べる。
- isFull()
    - キューが満杯かどうか調べる。

###実装

- Q
    - データを格納するための整数型1次元配列
- head
    - 先頭ポインタである整数型変数
- tail
    - 末尾ポインタである整数型変数
- enqueue(x)
    - キューに要素を追加する関数
- dequeue()
    - キューの先頭から要素を取り出す関数

##コード
```c
#include <stdio.h>
#include <string.h>
#define LEN 100000

typedef struct
{
    char name[100];
    int time;
} Process;

/* global variable */
static Process Q[LEN];
static int head, tail, n;

/* enqueue */
void enqueue(Process process_obj)
{
    Q[tail] = process_obj;
    tail = (tail + 1) % LEN;
}

/* dequeue */
Process dequeue()
{
    Process process_obj;

    process_obj = Q[head];
    head = (head + 1) % LEN;

    return process_obj;
}

int min(int a, int b) { return a < b ? a : b; }

int main(void)
{
    int elapse_time = 0;
    int time_ms;
    int qms;
    Process process_obj;

    /* input */
    scanf("%d %d", &n, &qms);
    for (int i = 1; i <= n; i++)
    {
        scanf("%s", Q[i].name);
        scanf("%d", &Q[i].time);
    }

    /* initialize */
    head = 1;
    tail = n + 1;

    while (head != tail)
    {
        process_obj = dequeue();
        time_ms = min(qms, process_obj.time);
        process_obj.time -= time_ms;
        elapse_time += time_ms;

        if (process_obj.time > 0)
            enqueue(process_obj);
        else
            printf("%s %d\n", process_obj.name, elapse_time);
    }
    return 0;
}
```

##ポイント
- 使われなかったクオンタムが持ち越されることはない。
    - 20 - 100 = 0となってループが進んでいく。
- モジュロ演算をすることでキューが円環状につながってループする。


##所感
- 見ていた解説の変数名が簡略化されすぎていたので、補った。
- 丁寧にデバッグしながらでないと理解できなかった。
- 円環の形をイメージすると、headとtailの概念がわかりにくくなるので、ところてん式のイメージを持って、取り出し→処理→格納の感覚でみた方がよい。

所要時間 180分

【復習】

- 2020/04/05
    - 自分で書いたら下記の書き方になった。こっちのほうが良さそう。
    - キューを全体を操作するのではなく、headとtailを操作する。
    - モジュロ演算でキューをクリアしながら使うという考え方は忘れていた
    - 未実装
    - 所要時間：80分

```c
    while (head != tail)
    {
        process_obj = dequeue();
        if(process_obj.time > qms){
            process_obj.time -= qms;
            elapse_time += qms;
            enqueue(process_obj);
        } else {
            elapse_time += process_obj.time;
            printf("%s %d\n", process_obj.name, elapse_time);
        }
     }
```
最近まで素人だった人が書くArduino入門

#筆者がこのブログを通してやりたいこと
僕と同じ趣味の人を増やしたい
ただ、それだけです。
#このブログの特徴
このブログの著者はちょっと前に「Arduino」を知ったばかりです。
なので**初心者の方がどこでつまずくかが分かります**！！
ぜひ読んでください。
また、だいぶ噛み砕いて書いているので、厳密な情報が欲しい方にはこのブログはおすすめできません。
#Arduinoとは
ちょー簡単に電子工作ができるマイコンという物です。
マイコンって何？と思ったと思います。

####マイコンとは、**スイッチ＋電圧計＋電卓**です。
スイッチ、電圧計、電卓を組み合わせて自分たちがさせたい動作のプログラミングをします。

#難易度は？
人によって違うと思いますが、興味があってこのサイトを見るほどの好奇心があれば多少の苦難ものりこえられると思います。
確実に**今皆さんが思っているよりも難しくないです！！**

#さあ始めよう

arduinoで電子工作をする上で、arduinoのほかにセンサーやLEDや表示機などが必要になります。
そのようなものがセットになったものがこの部品セットです。
[部品セット](https://amzn.to/3bP467q)
僕の記事の入門・初級者編に必要な部品はすべてこの中に入っているので、これ一つで部品が揃います、おすすめです。

入門編：
● [ArduinoIDEの使い方](https://qiita.com/Hizuki10301030/items/caace10b57fbe8696918)
●  [初めの一歩(Lチカ&hello world)](https://qiita.com/Hizuki10301030/private/ccdbb3656c791361142d) 
●[arduinoの中の電圧計を使ってみよう](
 https://qiita.com/Hizuki10301030/private/6d0664dac7fb4ca07899)
●[arduinoの中の電卓を使おう!!](https://qiita.com/Hizuki10301030/private/61b921da6627d5ab8820)
初心者編：
●[Arduinoで自作楽器を作ってみよう！](https://qiita.com/Hizuki10301030/private/460d1914b1f18cccfed3)

中級者編：
- [3日でラジコンを作ろう！！]()(準備中)

**ものつくり系のブログの醍醐味はブログの内容をやるだけではなく、やり終わった後にいかに自分で改造するか**だと思っています！
ぜひ改造してみてください。
CakePHP2のセッション切れ checkAgentの巻

とある CakePHP2 で作られたシステムで不定期にセッションが切れてしまうという現象があったのですが、その原因が判明したので書き記しておきます。必ずこれがセッション切れの原因というわけではなく、あくまでも一つのケースです。

結論から書きますと、CakePHP2 の checkAgent という機能と、ブラウザのラピッドリリースの相性の悪さが原因となります。

[CakePHP 2.X Cookbook - セッション#セッションの設定](https://book.cakephp.org/2/ja/development/sessions.html#id2) に

> Session.checkAgent - ユーザーエージェントはチェックされるべきです。 ユーザーエージェントがセッションとマッチしない場合、そのセッションは破棄されます。

とあります。checkAgent 機能ではセッションキーとともにブラウザの UserAgent も照合され、合致しない場合はセッションを継続できません。そして checkAgent 機能はデフォルトでは有効になっています。

checkAgent 機能は、攻撃者がセッションキーを奪取してなりすましアクセスをしようとしても UserAgent を再現できなかった場合には不正アクセスを防ぐことができるというものです。セキュリティ的には有益な機能ですが、問題は UserAgent の不変性です。

昨今の多くのブラウザはラピッドリリースを採用していますし、リリースの反映も自動的に行われるようになっています。早ければ数日程度の短期間に、ユーザが気付かない内にブラウザのバージョンアップが行われています。そして、UserAgent にはブラウザの詳細なバージョン情報も格納されています。例えば現在私が使っているブラウザの UserAgent は `Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.149 Safari/537.36` です。`80.0.3987.149` という詳細なバージョン情報が入ってますね。おそらく数日後にはここは変化していることでしょう。UserAgent が変わってしまうと、CakePHP2 は同一ユーザではないと認識し、セッションが破棄されます。

セッションタイムアウトを1日以内程度の短い時間に設定している場合は checkAgent 機能を有効にしても問題ないですが、何日にも渡ってセッションを有効にしたい場合には不適です。そして今回のシステムもセッションタイムアウトを長期間に設定していました。

checkAgent 機能はセキュリティ的には有益な機能ですが、現在のブラウザリリース事情には残念ながら合っていません。実際、CakePHP3 ではこの機能は削除されています。

checkAgent 機能はデフォルトで有効になっているため、無効にするには `app/Config/core.php` を以下のように書き換えます。

```php
--- a/app/Config/core.php
+++ b/app/Config/core.php
@@ -227,7 +227,8 @@
  * the cake shell command: cake schema create Sessions
  */
        Configure::write('Session', array(
-               'defaults' => 'php'
+               'defaults' => 'php',
+               'checkAgent' => false
        ));

 /**
```
lombokでデフォルトコンストラクタが無くてNoSuchMethodException

凡ミスの記録。

lombokを使用して以下のコードを実行したところ、実行時エラーになった。

```java
@Data
@AllArgsConstructor
public class Person {
  ...
```

```java
Caused by: java.lang.InstantiationException: kagamihoge.springbatchsample.Person
	at java.base/java.lang.Class.newInstance(Class.java:571) ~[na:na]
	at org.springframework.batch.item.file.mapping.BeanWrapperFieldSetMapper.getBean(BeanWrapperFieldSetMapper.java:248) ~[spring-batch-infrastructure-4.2.1.RELEASE.jar:4.2.1.RELEASE]
	... 53 common frames omitted
Caused by: java.lang.NoSuchMethodException: kagamihoge.springbatchsample.Person.<init>()
	at java.base/java.lang.Class.getConstructor0(Class.java:3350) ~[na:na]
	at java.base/java.lang.Class.newInstance(Class.java:556) ~[na:na]
	... 54 common frames omitted
```

原因は、引数無しのデフォルトコンストラクタが無いのでリフレクションによるインスタンス生成に失敗していた。

というわけで、lombokで引数無しコンストラクタも生成するように指定した。

```java
@Data
@AllArgsConstructor
@NoArgsConstructor
public class Person {
  ..
```
ArduinoIDEの使い方

#ArduinoIDEのインストール
僕は個人的にArduinoIDEは、どのプログラミング環境よりも構築が簡単だと思っています
使用しているPCが
windowsなら、MicrosoftStoreか[arduinoの公式ページ](https://www.arduino.cc/en/Main/Software)でインストールできます。
linux/macなら[arduinoの公式ページ](https://www.arduino.cc/en/Main/Software)でインストールできます。

#ArduinoIDEの使い方の基本的な流れ
プログラムを書く
　　　↓
コンパイルする(arduinoが理解できる言語に翻訳)
　　　↓
arduinoに書き込む

以上です。

#使い方
arduinoIDEにはいくつかのボタンがあります。
![プレゼンテーション1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/528717/0dc3041c-3cf8-5d15-c8e3-4233066f6da8.jpeg)
####保存：
書いたプログラムを保存する時に使います。保存をしないとarduinoIDEを閉じたときにプログラムが消えるので気を付けましょう。
####新規スケッチ:
新しいプログラムを書きたい時に使います。
これを押すとarduinoIDEがもう一つ作成されます。

####コンパイル：
プログラムが間違っていないかなどをチェックします。
例えば
a=5;をa===5;などと書くと「＝」が多いよと教えてくれます

####コンパイル＆書き込み：
コンパイルした後でarduinoにプログラミングを書き込んでくれます。
これでarduinoが自分がプログラミングをした通りに動作してくれます。
注意：後ほど説明しますが事の期にシリアルポートの指定を忘れないでください。

####シリアルモニター：
今はとりあえず分からなくていいです。
サイト内でシリアルモニターを見てくださいという指示があれば、このボタンを押してください。

#＊注意：シリアルポートの指定
PCに接続してArduinoには一つずつCOM○という番号が割り振られます
####COMとは：
簡単に言えばUSBにつないだデバイスに割り当てられた番号です。
複数台の機器をUSBにつないだ場合どれを操作の対象にするかを選択するためにあります。

####シリアルポートの指定
![プレゼンテーション２.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/528717/31bf8c1d-1bcd-5407-07a5-9d8a11cfc004.jpeg)
ArduinoをPCに接続した状態で　*ツール＞シリアルポート*　と進んでいくと写真のよにCOM○という番号が出てきます。
これは接続したarduinoに割り振られたCOMの番号です。
これを選択してからarduinoにプログラムを書き込んでください。（筆者はこれで１週間苦戦しました）

#最後に
基本的にこのボタンだけ覚えておけば問題ないと思います。
それでは、お疲れさまでした！
Mac初心者、買って1年のトラックパット異常に震える

今日は表題のトラブルがあったので共有します。
そう、トラックパッドが反応しなくなりました。新品で買ってちょうど1年ぐらいで、macBookProというハードでのトラブルは初めてだったので、すごく焦りました。
# トラックパッドをしっかり拭き掃除したら、直った。
結果、どうやって直したかというと、下記の記事を参考にしっかりトラックパッドを拭いて、再起動したら直りました。
見た目では見えにくい汚れがいっぱいついてたんです。

TechRacho様[MacのMagic Trackpadの不具合を修正する方法]
https://techracho.bpsinc.jp/hachi8833/2018_05_02/55798

PRAMクリアとかSMCリセットで改善する方法は他の色々なサイトさんで紹介されていたのですが、物理的な汚れを原因をとして挙げられていたのは、私が見た限りこちらの記事だけでした。
同じようなトラブルで今戦々恐々としてる方にこの記事が届いたら幸いです。
C++でボタンのテキストを変更してみた．

#環境
Kotlin : 1.3.71
Android Native Development Kit (NDK) : 21.0.6113669
CMake : 3.10.2
LLBD : 3.1

#コード
```kotlin:MainActivity.kt
class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        button.setOnClickListener {
            changeTextOf(button)
        }
    }

    external fun changeTextOf(btn: Button): Unit

    companion object {
        init {
            System.loadLibrary("native-lib")
        }
    }
}
``` 

```C++:native-lib.cpp
extern "C" JNIEXPORT void JNICALL
Java_com_example_foo_MainActivity_changeTextOf(
        JNIEnv* env,
        jobject /* this */,
        jobject btn) {
    jclass clazz = env->FindClass("android/widget/Button");
    jmethodID setText = env->GetMethodID(clazz, "setText", "(Ljava/lang/CharSequence;)V");
    std::string str = "success!!!";
    jstring arg =  env->NewStringUTF(str.c_str());
    env->CallVoidMethod(btn, setText, arg);
}
``` 

native-lib.cppの2行目について，パッケージの名前がcom.example.fooだったら，Java_com_example_foo_MainActivity_changeTextOfとなる．ここは自分のパッケージ名に合わせて修正．
以上のコードを実行すると，IDがbuttonのボタンをタップしたら，ボタンのテキストがsuccess!!!になる．以下，簡単にコードを説明．

#FindClass()
android.widget.ButtonのsetText()を使いたいので，FindClassの引数には'.'を'/'に置き換えた"android/widget/Button"を渡す．

#GetMethodID()
引数の1つ目はFindClassの戻り値，2つ目は使いたいメソッドの名前，3つ目は使いたいメソッドの引数．
3つ目の引数"(Ljava/lang/CharSequence;)V"は，"(引数)戻り値の型"となっている．Button.setText()は引数にCharSequenceをとり，値を返さない．なので，戻り値の型はVoidのVになっている．
詳しくは，[JNIの型とデータ構造](https://docs.oracle.com/javase/jp/1.5.0/guide/jni/spec/types.html)へ．

#CallVoidMethod()
setText()には戻り値がない(Void)ので，setText()を呼び出すためにCallVoidMethod()を使う．Callの直後には使いたいJavaのメソッドの戻り値の型が来る．CallVoidMethod()の引数の1つ目は変更するボタンのオブジェクト(jobject)，2つ目はGetMethodID()で取得したメソッドID，以降は使いたいメソッドの引数が来る．setText()はボタンに表示したい文字列を引数にとるので，これをCallVoidMethod()の引数の3つ目に渡す．

#参考文献
[JNI関数](https://docs.oracle.com/javase/jp/1.5.0/guide/jni/spec/functions.html)に様々な関数の説明がある．
[Java Native Interfaceを使用する上でのベスト・プラクティス](https://www.ibm.com/developerworks/jp/java/library/j-jni/)にも目を通しておきたい．
CSSの position: absoluteとrelativeのデフォルトにmargin:autoを設定した際の挙動の相違についての調査

【やったこと】
position: absoluteとrelativeのそれぞれデフォルト(top,left,rightの設定なし)でmargin:autoの併用を実施。挙動がことなるため調査を実施。

【わかったこと】
Chrome Developer Toolsにて属性の確認を実施。positionのデフォルトが異なるためにabsoluteは左寄り、relativeは中央に配置されることがわかった

※詳細は下記ブログに記述
[【第3回】CSSの position: absoluteとrelativeのデフォルトにimargin:autoを設定した際の挙動の相違についての調査](https://stchan-web.blogspot.com/2020/04/3css-position-absoluterelativeimarginau.html)
ほこりセンサーGP2Y1026AU0FをRaspberry Piから試す

空気清浄機などに内蔵されている「ほこりセンサー」という電子部品があります。秋葉原でもあまり見かけない部品のように思いますが、ネット通販で購入できます。

部屋のほこりの量を可視化できたら面白そうだと思ったので、シャープのほこりセンサーGP2Y1026AU0Fを入手してRaspberry Piから動かしてみました。

## 機種選定

[シャープのほこりセンサーは6種類ある](https://jp.sharp/products/device/lineup/selection/opto/dust/index.html)ようで、一番入手しやすそうなのがGP2Y1010AU0Fというアナログ出力のユニットです。しかし、私はRaspberry Piから使いたかったので、デジタル出力の方が都合が良い[^1]という事情がありました。

[^1]: Raspberry Piにはアナログ入力ピンが無いので、別途ADコンバータやArduinoなどを準備する必要があり面倒です。

そこでシャープのセンサーの中でデジタル出力のものを探しました。条件に合うセンサーユニットは下記の3つです。

- GP2Y1023AU0F
- GP2Y1026AU0F
- GP2Y1030AU0F

正直なところどれでも良かったのですが、探した中で一番安そうなGP2Y1026AU0Fを選びました。AliExpressで2個12ドルくらいでした。

## 外見

センサーの大きさは46mm x 36mm、高さ18mmくらいです。下の写真はRaspberry Pi Zeroと並べて撮ったものです。

![dust_sensor.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46856/2da7cb5c-6aae-dfd4-9891-6a03d69721ec.jpeg)

## Raspberry Piの準備

今回利用するGP2Y1026AU0FはUART接続になります。

Raspberry Piでは8番ピンと10番ピンがUARTに対応します。しかし、これらのピンは標準状態ではシリアルコンソール接続に使われているため、これを解除してUARTを有効にする必要があります。

具体的には下記の2ファイルを編集します。

```/boot/cmdline.txt
# 下記のように、「console=serial0,115200」を削除
console=tty1 root=PARTUUID=xxxxxxxx-02 rootfstype=ext4 elevator=deadline fsck.repair=yes rootwait
```

```/boot/config.txt
# ファイル末尾に下記を追加
[all]
enable_uart=1
```

これらの変更を行ってからOS再起動をするとGPIOからUART接続したデバイスの情報が取得できるようになります。パスは`/dev/serial0`などになるはずです。

# 動作確認

動作確認に使ったデモプログラムはGitHub上で公開しています。

- [hnw/go\-gp2y1026au0f: Demo code for Sharp GP2Y1026AU0F dust sensor](https://github.com/hnw/go-gp2y1026au0f)

GP2Y1026AU0Fからは3本の線が出ているのですが、黒をGND、赤を5V電源に接続します。白は10番ピン（GPIO 15）に接続します。通電させるとすぐに測定が始まります。カタログスペック上は70msごとに情報が取れるようです。

# 動作結果

単に通電しただけの状態ではセンサーは無反応で、ほこり0の表示になっていました。

ほこりセンサーの真上でティッシュペーパーを揉んだり破いたりしてみると、次のようにセンサーが反応しました。

```
（略）
VoutH=0, VoutL=0, VrefH=0, VrefL=11, Vout=0mV, dustDensity=0ug/m3
VoutH=0, VoutL=0, VrefH=0, VrefL=11, Vout=0mV, dustDensity=0ug/m3
VoutH=0, VoutL=0, VrefH=0, VrefL=11, Vout=0mV, dustDensity=0ug/m3
VoutH=0, VoutL=158, VrefH=0, VrefL=11, Vout=771.484375mV, dustDensity=220.42410714285714ug/m3
VoutH=0, VoutL=158, VrefH=0, VrefL=11, Vout=771.484375mV, dustDensity=220.42410714285714ug/m3
VoutH=0, VoutL=158, VrefH=0, VrefL=11, Vout=771.484375mV, dustDensity=220.42410714285714ug/m3
（略）
```

ほこりを検出する機能自体は期待通り動いているようです。

（当然のような気はしますが）部屋のほこりの増減を測定するような用途にはエアフローの確保が必須のようです。ファンでも取り付けますかね…

## 参考URL

- [ほこりセンサユニット｜製品ラインアップ｜電子デバイス/ディスプレイ：シャープ](https://jp.sharp/products/device/lineup/selection/opto/dust/index.html)
- [GP2Y1026AU0F SPECIFICATION.pdf](http://www.socle-tech.com/doc/IC%20Channel%20Product/Sensors/Dust%20Sensor/GP2Y1026AU0F%20SPECIFICATION.pdf)
- [Application Guide for Sharp GP2Y1026AU0F Dust Sensor · sharpsensoruser/sharp\-sensor\-demos Wiki](https://github.com/sharpsensoruser/sharp-sensor-demos/wiki/Application-Guide-for-Sharp-GP2Y1026AU0F-Dust-Sensor)
Teams ライブイベント　やってみた

Teamsの会議は、最大250名まで参加できるし、双方向のやり取りも可能だし便利。ただ、300が枷になっててそれ以上は参加できない。

この300の枷が10,000になっているのがTeams ライブイベント。双方向ではなくて一方通行の配信にはなるけど、さすがに10,000人と双方向するようなイベントは考えにくいし、一方通行で十分。

というわけで、何度か使っている中で、注意していることをまとめてみた。

ライブイベントをミニマム構成で行う
便利なところ
ライブイベントの制限
途中で落ちたら？
配信元を複数にしたいなら



#ライブイベントの最小構成

必要な道具は、デバイスとアカウント各1。
Teamsアプリから、予定表 - 下向き矢印　→　ライブイベント、からURLを作成できる。
デフォルトでは、作成するアカウントは「プロデューサー」になっている。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/237698/d6860f83-c863-b722-7835-330449076b2d.png)

視聴する方にはURLを案内すればOK。
プロデューサーは時間になれば、会議に参加。ライブの送信、開始すれば配信が始まる。

イベント終了後、終了ボタンを選択することで、イベントの配信が終了する。

#便利なところ

参加者リストが取れる。
テナント内の場合、だれが、いつ、参加した離脱した、ユーザーエージェントなどがエクスポートできる。iOSからTeamsアプリ、Windows10でChromeから、Trident（IE)からなんてことも。

配信がらくちん。
わざわざ録画を別案内しなくてもURL1つでいい。スピードアップ再生もできる。

一番便利なのは、300人の枷がないこと。

20200913追記
現在はTeams会議は300名まで参加可能になっているようです。[Microsoft Teams の制限事項と仕様](https://docs.microsoft.com/ja-jp/microsoftteams/limits-specifications-teams#meetings-and-calls)

#ライブイベントの制限
最大、4時間まで、という制限がある。4時間を超えるイベントの場合は、あらかじめライブイベントを2つ作成しておき、タイミングに合わせて切り替えるよう案内すればOK.

それから、20秒の追っかけ再生になる。Teams会議と異なり、録画しながら、その録画を配信する構成になっている。
視聴する側が、「ライブ」と選んでも、追っかけ再生になるので注意。

#途中で落ちたら？

会議URLはイベント開催中は有効。予定表で作成した時間とは関係なく、イベント開催中という点に注意。
イベントの終了は「終了ボタンを選択する」「開始から4時間経過」いずれかまで。


途中で何かの理由で会議の配信ができなくなってしまったら、プロデューサーのアカウントから慌てず「退出」する。そのあと、再度会議URLに参加すれば継続して配信できる。
再参加するまでは、画面も真っ暗になるかもしれないけど、途中で止まるわけではないので慌てずに退出がポイント。

どうしても心配な時は、PCを2台用意。
・両方、プロデューサーのアカウントでTeamsアプリにサインインしておく。
・プライマリ側でライブイベントを行っておき、トラブったら退出。
・すぐにセカンダリー側でイベントに参加し、ライブ送信を再開する。
としておけば心配も少なくて済む。

#配信元を複数にしたいなら

たとえば、イベント前半は会場Aから配信、イベント後半は会場Bから配信、なんてことをする場合につかう。

Teamsアプリでライブイベントを作成する際に、プロデューサー以外に発表者を設定しておく。

発表者：カメラと共有を行うひと
プロデューサー：どの映像を配信するか操作する。それと、発表者も兼ねる。

発表者は、イベント開始後、カメラとマイクをアクティブにしておいて、スタンバイ。
プロデューサーが、どの映像を配信するか選んで、切り替えるだけでOK。


#その他

資料と話者を同時に写す場合は、通常のTeams会議と手順がことなる。プロデューサーで配信したい「共有（デスクトップやウィンドウ）」と、配信したいカメラ１つ、を選択して配信できる。


参考にした資料：Teamsのライブイベントについて
https://docs.microsoft.com/ja-jp/microsoftteams/teams-live-events/what-are-teams-live-events
MTUを1502 byteにしないとscpできない現象に遭遇

ホストOSからゲストOSである仮想マシンに向けてscpをしたのですが、１バイトも送ってくれません。色々調べていくうちに仮想マシン側でMTUを1502バイトにすると送れる現象に遭遇しました。

原因はUSB-LANアダプタのドライバだったようです。最新版のドライバをインストールしたら不思議な２バイトのtrailerはなくなりました。

## 問題の現象

* 成功$ ping -c 1 -M do -s 1470 192.168.1.1
* 失敗$ ping -c 1 -M do -s 1472 192.168.1.1

MTUは1500バイトなので1472バイトでも成功するはず。何故か成功しません。ホストOSからゲストOSに向けたscpでは、数バイトのデータは転送できますが、約2KB以上では転送できません（scpがだんまり）。

### 環境

* ホストOS: Ubuntu 18.04(192.168.123.1)
* ゲストOS: VyOS 1.1.8(192.168.123.254, 192.168.1.254), CentOS 7.4(192.168.1.1)
* ホストOSとゲストOSの通信では、マザーボード備え付けのLANアダプタではなく、USB3ポートに指したUSB-LANアダプタを使用（BAFFALO LUA4-U3）

## 調査結果

* ホストOS／ゲストOSともにMTUは1500
* ゲストOS側のMTUを1502バイトにすると問題はなくなる（でも設定としてはおかしな設定なのですぐに戻す）
* マザーボード備え付けのLANポートを使う場合は見られない現象（マザーボードのLANポートを使う場合はなんの問題もなし）
* WireSharkで通信データを見てみると、データの末尾に「<font color="DarkRed">VSS-Monitoring ethernet trailer</font>」という２バイトのデータが付加されている。<font color="DarkRed">ん？</font>

## 解決策

参考資料に挙げたように、同じ現象に遭遇された方がいらっしゃいました。

その方の対策を真似て、AX88179のLinuxドライバ・ソースファイルをダウンロードしてインストールし直したら、「VSS-Monitoring ethernet trailer」は無くなりました。

## 参考資料

* https://www.dynatrace.com/news/blog/openstack-network-mystery-2-bytes-cost-me-two-days-of-trouble/
アソシエーション分析を活用したレコメンデーションのチュートリアル(概念編)

#この記事について
あまり世間にレコメンドに関してサンプルデータを使って実装したチュートリアルが無かったので記事を書きました。<br>レコメンデーションを作成する手法は機械学習などを使った手法などがありますが、これは統計よりの手法を使ったレコメンデーション作成方法の記事です。<br>
pythonとオープンデータセットを用いて説明をしていきます。

#レコメンドとは
そもそもレコメンドとは何かですが、**顧客にとって関心があると思われる商品、サービスなどを提供者側から薦めること**です。<br>
下に●MAZONの例を示しますが、ある『掛け布団』の商品ページを見るとそのレコメンド商品として**『掛け布団カバー』**と**『敷布団』**がレコメンドされています。


![20200312_レコメンドについて (1).jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/151192/0168f760-9cda-65c7-4305-adf3e745dc23.jpeg)

『掛け布団』と『掛け布団カバー』『敷布団』は確かに関連がありそうで、一緒に買ってしまう人もいるかと思います。<br>
まさにこれが狙いで、レコメンドを行うことにより俗に言う『連れ買い』や他商品の認知をさせることができます。

#レコメンドの種類
レコメンドは大きく分けて**『コンテンツベース』**と**『トランザクションベース』**の２つがあります。
![20200312_レコメンドについて (2).jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/151192/caf9e95a-9ceb-dec6-8e80-4c639b6c1096.jpeg)

それぞれメリットデメリットがありますが、複合的に使うことができますので互いのデメリットを解消し合うことが可能です。

#アソシエーション分析を活用したレコメンデーションについて
この記事でのテーマであるアソシエーション分析を活用したレコメンデーションは以上の種類のうちの**『トランザクションベースレコメンド』**にあたります。<br>
そして先ほどの●MAZONの例の『掛け布団』に対して『掛け布団カバー』と『敷布団』をレコメンドするのも『トランザクションベースレコメンド』になります。<br>

<img width="565" alt="スクリーンショット 2020-04-04 19.26.00.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/151192/660b5144-74be-11c8-daeb-af0dacc8cbfb.png">


**『トランザクションベースレコメンド』は基本的に『連れ買い』された商品が出やすい結果となります。**<br>
※逆に『コンテンツベースレコメンド』の場合は『類似している』商品がでることが多く、掛け布団の場合であれば他のメーカー掛け布団などが出やすい結果となると思います。

#アソシエーション分析とは何か
アソシエーション分析とは、例えば「商品Xを買われた時に商品Yは同時に（もしくは次に）買われやすい」という商品XYの関連性を明らかにすることです。これはレコメンドで行いたいことそのものですね。<br>

アソシエーション分析は統計的なアプローチで、詳細な説明や理論は[こちら](https://bdm.change-jp.com/?p=1341)のサイトに非常によくまとまっております。よって詳細な説明や理論はこちらのサイトをご確認いただき、この記事ではより理論抜きで抽象的な概念を説明していきます。<br>


## アソシエーションの分析手法
アソシエーション分析において関連性を評価できる手法は2つあります。
**1.　確信度（Confidence）を用いる方法
2.　リフトを用いる方法**

ちなみにこの記事では**2のリフト値を用いる方法**を採用します。2は１がベースとなりますので、まず１から以下に説明していきます。

###1.　確信度（Confidence）の考え方
簡単にいうと、ある商品Xが買われた時に同時に（もしくはその次に）変われる商品Yを見つける手法です。
以下の図をみてください。
![20200312_レコメンドについて (3).jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/151192/ade4e817-2d1a-e38c-54ca-6474abef012c.jpeg)

まず小規模な例ですが、以上のように先ほどの掛け布団を買った顧客のデータを抜き出してみたとします。<br>
これを見ると６人のうち、掛け布団を購入後に布団カバーを2人、ミネラルウォーターを2人、他の商品は1人づつという結果になってます。<br>この結果だけを見ると**掛け布団と関連性が高いのは布団カバーとミネラルウォーターということになります。**

この考え方が**確信度(confidence)**の考え方です。

###2.　リフトの考え方
1の確信度の考え方には一つ考慮すべきポイントがあります。以下の図をみてください。
![20200312_レコメンドについて (4).jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/151192/7854f928-3e82-9d0c-1063-a24a244adde8.jpeg)

仮にこの6人の顧客のデータをもう少し集めたとしましょう。<br>上の例だと、ミネラルウォーターはそもそもメジャーな商品で掛け布団とは関係なく頻繁に購入されています。この場合、ミネラルウォーターは掛け布団のみと関連性が高いということは疑問に思えてきます。<br>

しかし結果的にミネラルウォーターが買われることが多いのであれば、その商品Xに対してもミネラルウォーターをレコメンドしておけばいいのではと考えるかもしれません。<br>
これが一概にダメだとは言い切れないのですが、個人的に以下を考えます。
　　　　1. そもそもメジャーな商品は認知されているためレコメンドする必要がない
　　　　2. 顧客側から見たときに、レコメンド商品として違和感を感じる


**リフトの考え方では、このようなメジャーな商品は省き、商品Xに特徴的な関連商品Yを見つけることが可能になります。**<br>
実際は[こちら](https://bdm.change-jp.com/?p=1341)のサイトにあるようにリフト値というものをトランザクションデータから算出し、それを元に関連性の高い商品XYのペアを導いていくといく流れになります。

#サンプルデータを用いたチュートリアル
[こちら](https://qiita.com/tachiken0210/items/6873191f9ba5c6f491ed)に記事を追加しました。
BungeePortalsの使い方

# はじめに
書いてる人全然見つからなかったため[こちら](https://www.spigotmc.org/resources/bungeeportals.19/)のプラグインの使い方を備忘録で残します。

# １. ゲート作成
1. WorldEditの範囲選択でゲートにしたい範囲を選択。
2. `/bportals select <ID>`で`<ID>`部分に範囲内にあるブロックのIDを入力して実行。※必要なブロックのみで可
3. `/bportals create <鯖名>`でつなげたい鯖を選び完成
# ２. ゲート削除
また今度書くね
curl を使っているPHP スクリプトで https がエラーになる件の解決方法

Moodle の管理をしていて、ハマった事項を解決したので共有します。

「言語パック」をクリックすると環境によってエラーになる問題です。
Moodle のダウンロードサイトから https 通信により curl コマンドで言語パックファイルをダウンロードしようとして、エラーになってしまうのです。AWSのインスタンスで、出たり出なかったりしました。

プログラムの動作としては、curl コマンドを内部で実行しているのですが、デバッグ
してみたところ、lib/filelist.php で以下のように PHP の curl エラーになっています。

```
[77] => 'CURLE_SSL_CACERT_BADFILE',
```

要すれば、curl が俺が使うためのCACERTファイルがない、と文句を言っているようです。
以下のサイトから、最新の cacert.pem をダウンロードして、一連の CACERT の仲間に
加えてあげることで、直りました。
（リンク）
https://curl.haxx.se/docs/caextract.html

たまに次の手順をやってあげる必要がありそうです。

1. 上記リンクからダウンロードした最新の .pem ファイルを以下にコピー。

  `/etc/pki/ca-trust/source/anchors`

2. 次のコマンドを実行

```
  # update-ca-trust
```

3. サービスを再読み込み

```
 # systemctl reload php-fpm
 # systemctl reload httpd 
```

（参考）
/etc/pki/ca-trust/source/README
（マニュアル）
man update-ca-trust
（PHP）
https://www.php.net/manual/ja/function.curl-errno.php
（関連）
https://stackoverflow.com/questions/23434792/php-curl-working-locally-error-77-on-aws-server
（近い）
https://gist.github.com/reinaldomendes/97fb2ce8a606ec813c4b
Pythonでアルゴリズム（幅優先探索、bfs）

#はじめに
　pythonを使った幅優先探索の実装について解説していきます。（僕がいつも実装するやつを載せるだけです。）
　幅優先探索ではよく距離についての問題が出てくるので、今回はある1頂点から各頂点までの距離を返す関数を実装します。
#幅優先探索
　幅優先探索に関する一般的な知識は調べればたくさん出てくると思うので、詳しくは省略しますが簡単に説明します。
　　　![89922.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/471565/fafe29f9-684f-abf5-fd3e-23a74b613a61.jpeg)
　青い矢印のように、近いところから順に頂点を追っていきます。今回扱う距離の場合には、ひとつ前の頂点までの距離に1を足せばいいです。（画像では1から振っていますが、距離ならば0から振ればいいです。）
　この頂点の探索の順番は、キューで管理します。キューは、先入れ先出しのデータ構造です。今回の例でいうと、まずはスタートの0が入ります。（[0]）次に、中身を前から取り出し、隣接する頂点を調べます。（今回は1, 2）初めて訪れたのであればキューに追加します。（[1, 2]）
　これを繰り返していけば青い矢印順に頂点を調べることができます。
（[2, 3, 4]→[3, 4, 5, 6]→[4, 5, 6, 7]...）
　キューが空になったら探索終了です。お疲れ様です。
#実装
##入力
　頂点数nと辺の数mが与えられ、その後隣接する頂点をm行に渡って与えられます。

```
11 9
0 1
0 2
1 3
1 4
2 5
2 6
3 7
5 8
8 9
```
##コード
```py
import sys
input = sys.stdin.readline

n, m = [int(x) for x in input().split()] # nは頂点の数、mは辺の数
g = [[] for _ in range(n)] # 隣接リスト

for _ in range(m):
    a, b = [int(x) for x in input().split()]
    g[a].append(b)
    g[b].append(a)

from collections import deque

def bfs(u):
    queue = deque([u])
    d = [None] * n # uからの距離の初期化
    d[u] = 0 # 自分との距離は0
    while queue:
        v = queue.popleft()
        for i in g[v]:
            if d[i] is None:
                d[i] = d[v] + 1
                queue.append(i)
    return d

# 0からの各頂点の距離
d = bfs(0)
print(d)
```
##出力
左から頂点の番号順に頂点0との距離を持つリストを出力します。自分との距離は0で、たどり着けない頂点はNoneとなります。

```py
[0, 1, 1, 2, 2, 2, 2, 3, 3, 4, None]
```
#おわりに
　何か間違いがあれば是非教えてください！アドバイスなどもいただけたらうれしいです！
GitHubの始め方

# はじめに

GitHubはソースコードのバージョン管理をオンラインで行えるウェブサービスです。
ここでは、GitHubのユーザー登録や、SourceTreeの初期設定の方法について解説します。

# GitHubのユーザー登録

[GitHub公式ページ](https://github.co.jp/)にアクセスし、「GitHubに登録する」をクリックします。

![github_top.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/517951/2fd3cfe2-3550-fe41-0720-29a25876937d.png)

ユーザーIDやメールアドレスなどの情報を入力します。

![github_register.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/517951/717b7034-6ff5-e327-508d-92264fb4b5d4.png)

入力したメールアドレスに確認メールが届くので、認証をして登録完了です。

# SoruceTreeの初期設定

ユーザー登録が済んだら、SourceTreeでリモートリポジトリとしてGitHubを登録します。
SourceTreeを立ち上げ、左上の「Remote」を選択し、「アカウントを追加」をクリックして立ち上がるウィンドウで、ホスティングサービスとして「GitHub」を、優先するプロトコルとして「HTTPS」を選択し、「OAuthトークンを再読み込み」をすると、GitHubをリモートリポジトリに追加することができます。

![github_sourcetree.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/517951/279912b3-84f9-c751-b12b-385a7df07b63.png)


# まとめ

ここでは、GitHubの利用を開始するにあたって必要な初期設定について解説しました。
以上の設定が終われば、GitHubにソースコードをアップロードできるようになります。
【UE4】PostProcessで雲行きを怪しくする

[1]:https://historia.co.jp/ue4petitcon13
[2]:https://youtu.be/E031FMxMJ8Q
[3]:https://qiita.com/Rinderon/items/5e526adcfdc4c104c745
[4]:https://www.slideshare.net/EpicGamesJapan/ue4-108770894


[株式会社ヒストリアさん主催の第13回UE4ぷちコン][1]応募後のあれこれの続き。
やったこと、やれなかったこと、誤魔化したところなどの整理と備忘録として。

この作品、途中でドラゴンが出現して、プレイヤーキャラの仲間の恐竜を食いに来る。その際、いわゆる「Warning!!」演出として、画面を暗くした。何やら雲行きが怪しい感じにしたかった。

# 使用前

ところが、当時は締め切り直前で完全にテンパっていたし、Post Process Volume すら置いていなかったので、レベルに最初から置いてあった Directional Light を青く暗くして誤魔化していた。

ドラゴン出現時には、「まず影がよぎって」その後「画面に登場する」という演出を狙って作っていたのだが、

![20200320_1929.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/358170/47a9173b-e50c-f09c-8160-3eecf363e638.gif)
（[当時の記事][3]）

作品内では演出のためのライトを暗くしてしまった結果、影がものすごく薄くなってしまった。画面の中のコントラストが妙に薄れてしまって、逆効果。すごく残念な絵に。

![20200403_2155_01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/358170/4734319d-a4b0-4268-a18d-5df4bc817cab.png)

# 使用後

…ということで、ライトを暗くする演出をやめて、Post Process Volume での演出に変更してみた。
※ドラゴン出現に合わせて、Post Process Volume の値を変更している。

![20200403_2155_02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/358170/56da17ba-d383-f61f-9675-b56780db17c0.png)

やはり影がしっかり出ている方が、何やら良く分からない危機感を感じられる …ような気がする。

【おまけ】カメラを Eject して撮った画像

![20200403_2155_05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/358170/2ad1d3cb-d54e-66eb-b137-2be9d94f596a.png)
かっこいい!?

![20200403_2155_03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/358170/7863f66f-ceda-9fa7-b09b-e439e7fc84f9.png)
ちゃんとしっかりはっきりドラゴンの影がよぎるようになった。

# Post Process の Color Grading をいじった。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/358170/83752454-a1dd-b0ef-9584-87a36d100b09.png)

そもそも、ライトで（特に太陽光=Directional Light）をいじってこういう演出をするのは邪道で、カラーグレーディングを使うべきである　…ようなことを、凄腕アーティストさんから聞いた気もする。

---

- [応募作品動画へのリンク][2]
- とてもありがたい、EGJのおかずさんの Slide Share：[猫でも分かるUE4のポストプロセスを使った演出・絵作り][4]
sshをとりあえず使う

#### 今はsshを何となく使うように今はなれればいいといい思いで書いています。。

```:SSH_Keyを作成
ssh-keygen -t rsa -b 4096 -C "email@example.com" -f ~/.ssh/id_rsa
```
オプション内容
`-t` - 鍵の種類を選択 `dsa`, `ecdsa`, `ed25519`, `rsa`から選択
`-b` - 生成する鍵のビット数を指定。rsa鍵の場合、最小のサイズは1024ビットであり、デフォルトは2048ビット。4096であれば安心
`-C` - コメント追加
`-f` - 鍵の格納先を指定

```:現在使用している鍵の暗号強度の確認
ssh-keygen -l -f ~/.ssh/id_rsa.pub

2048 SHA256:XXXXXXXX/XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX/XXX email@example.com (RSA)
```

```:秘密鍵のディレクトリパスを指定して接続
ssh -i 鍵のある場所のパス 接続先IP
```

```:接続時の詳細を表示
ssh -vvv 接続先IP
```

```:ファイル転送
scp -i 鍵のある場所のパス 転送元パス 転送先パス 
```

```:known_hostsから対象IPを消去
ssh-keygen -R 対象IP
```
[参照先1](https://kiririmode.hatenablog.jp/entry/20171020/1508485674)
[参照先2](https://qiita.com/Pana/items/70cc74cd20c8b5b4fe15)
Go言語の環境構築 

# Go言語の環境構築

備忘録がてら

## 実施環境
- macOS Catalina 10.15.3

## Home brewのインストール

割愛

## Goのインストール

```
$ brew install go
$ go version
go version go1.13.8 darwin/amd64
```

## GoPathの設定

```bash

$ mkdir $HOME/go
$ vi ~/.bash_profile

以下を追加
------------------------------------
export GOPATH=$HOME/go
export PATH=$PATH:$HOME/go/bin
------------------------------------

$ source ~/.bash_profile
```

## vscodeの設定

- Goの拡張機能を追加
- 便利ツールたちの追加
    - shift + command + P 
    - Go install/Update Tools をクリック
    - 全部にチェックを入れてOK

## Hello World

- $HOME/goの下に/srcを作成
- $HOME/go/srcの下にhogehoge(プロジェクト名)を作成

- $HOME/go/src/hogehogeに以下ファイルを追加

```main.go
package main

import "fmt"

func main() {
	fmt.Println("Hello, 世界")
}
```

- $HOME/go/src/hogehogeで以下を実行

```
$ go run main.go 
Hello, 世界
```

## Goのディレクトリ構成

ディレクトリ構成一例。
/bin,/pkg,/srcは基本

```
GOPATH
├── bin
├── pkg
└── src
    ├── hogehoge
    └── github.com
```

## goコマンドたち

```bash

# インストールコマンド　成果物は/bin直下
$ go install {プロジェクトフォルダ}

# ビルドコマンド　成果物は同じパス
$ go build {対象ファイル}

# 環境設定一覧(GOPATHなど)
$ go env 

```
Python3 データをプロットすると軸の範囲が変化してしまいます

(Python3.6.8　Shellを用いています)

入力するデータファイル(plot_graph_data.txt)を、
1 1.1
2 1.2
3 1.6
としてデータを読み込み、次のグラフを作成したいと考えています。(Hello Helloの描画は除く)

![2020-04-04 180949.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/613741/7f8c157c-52f9-feb9-98c6-b9ff61d4a030.png)

次のようなプログラムを書きましたが、
下図の実行結果のようにx軸,y軸の範囲が目的のグラフと異なる結果になってしまいました。

原因を教えてくださいm(_)m

自分の書いたプログラム
import matplotlib.pyplot as plt
fig, ax = plt.subplots()
x=[]
y=[]
fp = open('plot_graph_data.txt','r')
for i, line in enumerate(fp):
    data=line.split()
    x.append(data[0])
    y.append(data[1])
    
ax.plot(x, y, 'ro') # red circle
ax.set_title("My graph", loc="center")
ax.set_xlabel("time(s)", labelpad=None)
ax.set_ylabel("height(m)", labelpad=None)
ax.set_xlim(left=0.0, right=4.0)
ax.set_ylim(bottom=0.0, top=2.0)
plt.show()

実行結果
![Figure_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/613741/b33ad6c5-36ae-c1b8-637e-e2be79c3205f.png)
IBMクラウド Git リポジトリへのsshアクセス

IBM CloudのGitリポジトリにアクセスを求められたときの作業めも。
SSH設定しないとcloneできなかったので。。ハマりました。。
※ ベースはGit lab

1.SSH鍵生成
---
```
#ssh-keygen -t ed25519 -C アカウント名
Generating public/private ed25519 key pair.
:
```
2.生成された鍵をコピー
---
```
pbcopy < ~/.ssh/id_ed25519.pub
```

3.IBM Cloud(GitLab)にコピーした鍵を登録
---
アカウントのSSH鍵の画面で登録できる


4.テスト
---
```
ssh -T git@us-south.git.cloud.ibm.com
```


参考URL
---
* IBMCloud gitlab　SSHアクセス   
https://us-south.git.cloud.ibm.com/help/ssh/README

* Continuous Delivery(git環境)セッテイング
https://cloud.ibm.com/docs/services/ContinuousDelivery?topic=ContinuousDelivery-git_working#git_authentication

* Gitの簡単設定
https://us-south.git.cloud.ibm.com/help/gitlab-basics/start-using-git

その他
---
Gitを触っていた時の備忘。よく忘れる。。

コマンドメモ
--
|コマンド | 内容 |
| ---- | ------- |
|git remote -v   | 複数リポジトリの表示 |
|git remote add [laber] [リポジトリのURL]   | リモートリポジトリの追加 |
|git config --global -e   | Gitコンフィグのエディタ編集 |
|git config --global --list]   | Gitコンフィグの情報確認 |
|git branch -a | ブランチ表示 |
|git branch [branch名]  | ブランチ作成 |
|git branch -D [branch名]  | ブランチ削除 |
|git checkout [branch-name]   | ブランチ切替 |
|git add [オプション] [filename]  | ファイルをgit管理の対象にいれる |
|git push -u origin [branch-name]   | pushリクエスト |
|git fetch   | リモートリポジトリで更新された最新情報をローカルリポジトリに持ってくるコマンド |
|git commit -m   | お腹のファイルをローカルbranchにcommit |
|git branch --sort=committerdate| 更新順にブランチをソートして表示 |

※pull requestはコンソールから。
https://qiita.com/shh-nkmr/items/fde133cbdfa5f0092be1

GitConfigのパス
--
|OS | PATH |
| ---- | ------- |
|MAC | /usr/local/etc/gitconfig |
【エラー対処】TypeError: 'list' object is not callable


Python初心者がハマってしまったエラーへの対処を書きます。

＜エラー＞
TypeError: 'list' object is not callable

＜原因＞
関数であるlistを変数として定義してしまっている。

＜対応方法＞
１．whosで変数の一覧を確認し、listが変数として定義されていることを確認する。

```
whos
```
以下のように、実行結果を得られます。
listが変数として定義されてしまっています。

```
func        function    <function func at XXXXXXXXXXXX>

list        list        n=3
```

２．変数として定義してしまったlistを削除する。

```
del list
```

以上で、変数listを削除できました。
（もちろん、誤ってlistを変数定義している箇所の修正も必要。）
【Rails】Railsアプリでfont-awesome(5系)を使えるようにするには

#Font-awesomeとは
Web上で無料で使えるアイコンを提供しているツール

#Font-awesomeをアプリに読み込む
gemでインストールする

fontawesome4系では「gem 'font-awesome-rails'」でインストールできていたが、fontawesome5系には対応していないとのこと。よって最新版を使用するために次のgemをGemfileに追加しましょう。

```
gem 'font-awesome-sass'
```

gemを追加したらbundle install

```
$ bundle install
```

その後はapp/assets/stylesheets/application.scssにfont-awesomeを引き込んでおきましょう。
今回はscssを使う場合を想定しています。

```
@import 'font-awesome-sprockets';
@import 'font-awesome';
```

これで5系に対応しているfontawesomeがアプリ内で使えるようになる。

#参考
[font-awesome-sassについて/ピカワカ](https://pikawaka.com/rails/font_awesome_sass)

[gem 'font-awesome-rails'は最新版に対応してない... 代わりにfont-awesome-sassを使おう!](https://qiita.com/paudorino/items/d54348f6d48eefcee6c7)

[font-awesome-railsは5系をサポートしているのか？について](https://github.com/bokmann/font-awesome-rails/issues/194)