OmniAICreator/Qiita-1.07M huggingface dataset:
[FPGA] 複数のFIFOに対する配線遅延のばらつきを防ぐ



Vivado 合成の属性である KEEP[[1]](https://japan.xilinx.com/support/answers/54778.html)の使い方について一言メモ。KEEPを使うと、並列配線における局所の配線遅延を防ぐことができます。

一般的にタイミング制約と一緒に使います。
しかし、使用するロジックセル(Xilinxにおけるロジックデバイス。Alteraならロジックエレメント[[2]](https://www.macnica.co.jp/business/semiconductor/articles/intel/111977/))の数が少ない場合にはタイミング制約がなくとも機能するようです。
同時計測において配線遅延のばらつきが気になる場合には有効だと個人的には思っています。

何か質問やコメントがあれば、ご連絡ください。

## 参考
[1] [Vivado 合成のデザイン アシスタント - 合成 HDL 属性のサポート - keep、keep_hierarchy、ram_style、rom_style](https://japan.xilinx.com/support/answers/54778.html)
[2] [FPGA って何者？これから FPGA を始める人のための基礎知識](https://www.macnica.co.jp/business/semiconductor/articles/intel/111977/)
【Vue3】オブジェクトのプロパティを追加してもリアクティブに動作するようになりました

[【Vue.js】オブジェクトのプロパティを追加してもリアクティブに動作しなかった時の備忘録](https://qiita.com/kenji7157/items/153c207795f45709406b)にて、`Vue2.x`において、オブジェクトのプロパティを追加してもリアクティブに動作しないこと、またその解決策について書きました。


`Vue3`で同じことをしようとすると、どのような挙動になるのか確認してみました。結論を先に言ってしまうと、`Vue3`から**オブジェクトにプロパティを追加した場合もリアクティブに動作するようになりました。**

## Vue3環境の準備
vue-cliコマンドを利用して`Vue3`をインストールしていきます。`vue create`コマンドで`Vue 3 Preview`を選択します。（vue-cliがv4.5以上でないと`Vue3`環境は作成できません。）

```
vue create study-vue3
? Please pick a preset: Default (Vue 3 Preview) ([Vue 3] babel, eslint)
```
（ディレクトリ名は`study-vue3`としました。）

`npm run serve`を実行して以下の画面が確認できれば、インストールは無事に完了しています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/397734/ac527689-cc89-9ab2-3aa2-c788fb92db0d.png)


## HelloWorldを書き換える
オブジェクトのプロパティが`v-if`に指定されるよう`HelloWorld.vue`を以下に書き換えます。

```vue
<template>
  <div>
    <button @click="show">表示する</button>
    <p v-if="hoge.isShow">表示</p>
  </div>
</template>

<script>
import { reactive } from 'vue'
export default {
  name: 'HelloWorld',
  setup() {
    const hoge = reactive({})
    const show = () => {
      hoge.isShow = true
    }
    return { hoge, show }
  }
}
</script>
```

`Vue2.x`の場合、ボタンを押しても表示の文字が出ないことは、[【Vue.js】オブジェクトのプロパティを追加してもリアクティブに動作しなかった時の備忘録](https://qiita.com/kenji7157/items/153c207795f45709406b)の記事で説明しましたが...
 

`Vue3`から導入された`reactiveメソッド`によってこの課題が解決されました。

`reactiveメソッド`から返されるオブジェクトは、プロパティが追加された場合でも**リアクティブ**に動作させる事が可能になります。🙌🦒  

> [Reactivity API](https://v3.vuejs.org/api/reactivity-api.html#reactivity-api)
The reactive conversion is "deep"—it affects all nested properties.

【動作イメージ】
![Kapture 2021-02-13 at 01.30.39.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/397734/09fa8c80-858a-1322-9d0a-5cbbbbb61c93.gif)

## Vue3環境でVue2.xコードを書いて動作確認してみる

`Vue2.x`では、**リアクティブ**に動作しなかったコードを、`Vue3`環境で動かすとどうなるのか確認してみました。

```vue
<template>
  <div>
    <button @click="show">表示する</button>
    <p v-if="hoge.isShow">表示</p>
  </div>
</template>

<script>
export default {
  name: 'HelloWorld',
  data () {
    return {
      hoge: {
        // isShow: false, コメントアウトで未定義にしています
      }
    }
  },
  methods: {
    show () {
      this.hoge.isShow = true
    }
  }
}
</script>
```

`Vue3`では**リアクティブ**なプロパティとして認識されるようになっていました。
![Kapture 2021-02-13 at 01.30.39.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/397734/09fa8c80-858a-1322-9d0a-5cbbbbb61c93.gif)

この挙動になる理由について記載されたリファレンス等は見つかり次第追記していきます。🦒
【Vue】Vuetify.jsにコントリビュートするための準備

![スクリーンショット 2021-02-14 1.54.29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/397734/037b3ef2-dd0a-1386-7753-cb405f344cef.png)

`Vuetify.js`にコントリビュートしてみたい！という方に開発環境の構築を本記事でまとめました。


## コードをcloneする

```
git clone https://github.com/vuetifyjs/vuetify.git
```

以降のコマンドはすべて**clone**で取得した`vuetify`ディレクト配下で実行しています。

## yarnコマンドを使用できるよう準備

- npmからyarnをインストールする  

```
npm install -g yarn
```

## パッケージをインストールする
```
yarn
```

## ビルドの実行
```
yarn build
```

> [node-gyp](https://github.com/nodejs/node-gyp#installation)がグローバルなNode環境に入っていない場合はビルドに失敗します。 その場合は、`npm install -g node-gyp`の実行後に改めてビルドしてください。

## 開発サーバの起動


- 起動する前に、`packages/vuetify/dev/Playgroud.vue` を以下に書き換える

```vue:packages/vuetify/dev/Playgroud.vue
<template>
  <v-container>
    <p>ただいま開発環境の動作確認中</p>
  </v-container>
</template>

<script>
  export default {
    data: () => ({
    //
    }),
  }
</script>

```

- 開発サーバを起動する

```
yarn dev
```

- ブラウザから http://localhost:8080/#/page1 にアクセス

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/397734/7710057f-a9bc-11a6-6b57-36c3be98e1c6.png)

`Playgroud.vue`の内容がブラウザから確認できれば、vuetify.jsの開発環境構築は完了です。  

`issue`で上がっているバグを再現する際は、`Playground.vue`にコピペすると大抵は再現確認できるので、改修作業を行う際は`Playgroud.vue`を利用しましょう。👍

> PRを出す際は、既にMergeされているPRを参考に作成すると、レビューを見てもらいやすくなります。報告内容を`Fixes:xxx`だけにしないで、修正前後の挙動の違いについても記載すると良さそうです。

参考記事：https://vuetifyjs.com/en/getting-started/contributing/#working-with-github
SSHログインした時や作業中にどのサーバにいるか分かりやすくする方法

## 前座

皆さんこんにちは。ハンズラボのサムです！
今回は複数サーバにSSHログインしてるとあるあるなネタです！

**ターミナルでタブをいっぱい開いていると今自分がどのサーバにいるのか分からなくなる現象をどうにかしたい！**

今回はこれを解決したいと思います。

## 設定方法

### ログイン時のメッセージ設定

* /etc/motdに下記を追加
    * サーバ名
    * ドメイン名
    * IPアドレス

例

```
   ___             ___          __  _             ____                       ___              __
  / _ | ___  ___  / (_)______ _/ /_(_)__  ___    / __/__ _____  _____ ____  / _ \_______  ___/ /
 / __ |/ _ \/ _ \/ / / __/ _ `/ __/ / _ \/ _ \  _\ \/ -_) __/ |/ / -_) __/ / ___/ __/ _ \/ _  / 
/_/ |_/ .__/ .__/_/_/\__/\_,_/\__/_/\___/_//_/ /___/\__/_/  |___/\__/_/   /_/  /_/  \___/\_,_/  
     /_/  /_/                                                                                   
                                                                                  
Domain : Domain name
IP Address : Global IP Address
 ```

※AAはここで作れる (フォント : smslant)
https://aa.be-dama.com/

#### Amazon Linuxの時はmotdが自動更新されるので、設定で更新停止
> sudo update-motd --disable

### ターミナルの表示を変える

* /etc/bashrcに下記を追記
   * 表示情報のホスト名をサーバ名にする

例

```config
# Default Pronmpt Setting
#PS1="[\u@\h \W]\$"
PS1="[\u@AP-Prod \W]\$ "
```
\u@の後ろにサーバの名前を入れてください！

#### 変更前

```
[centos@ip-172-31-1-1 ~]$
```

#### 変更後

```
[centos@AP-Prod ~]$
```

以上になります！
どれも簡単に設定できて、サーバを間違えて操作ミスする可能性を減らしたり、確認作業をしやすくできるので是非試してみてください！
MySQLdbで文字コードエラー

こんなエラー

```
Traceback (most recent call last):
....
    cursor.execute(sql)
  File "/home/user/.local/lib/python3.6/site-packages/MySQLdb/cursors.py", line 188, in execute
    query = query.encode(db.encoding)
  File "/usr/lib/python3.6/encodings/cp1252.py", line 12, in encode
    return codecs.charmap_encode(input,errors,encoding_table)
UnicodeEncodeError: 'charmap' codec can't encode characters in position 486-487: character maps to <undefined>

```

対策
デフォルトでlatin-1を使うらしいので、接続時に明示的にエンコードコード方法を指定


```
conn = MySQLdb.connect(
    host=host,
    db=dbname,
    port=port,
    user=user,
    passwd=password,
    use_unicode=True,
★これ  charset="utf8mb4"
)

```
初めてのNext.js 開発: 公式チュートリアルを進める[Memo for neko]

<h1>公式チュートリアルを参考に</h1>
対象：すごーく初めての方
基本的には、Next.jsのチュートリアル英語版→日本語にして、さらに簡略化したメモです。
こちらを参考に、Next.jsのことを少しでも知ってもらえるキッカケになれば・・・
・参考URL：Next.js サイト：https://nextjs.org/
（基本的に上記の英語サイトを参考）

==環境==
・PC:Macbook Pro (Retina)
・macOS Big Sur

==今回の流れ（簡略）==
1. Next.jsのサイトへアクセス（https://nextjs.org/）
2. ”Start Learning”（学習スタート）ボタンからスタート
3. ”Create a Next.js App”（Next.jsを作成）ではじめにスタート

<h1>1.Next.jsのサイト</h1>
・Next.js サイト：https://nextjs.org/
（ここに全てのってます、英語で・・・）
<h1>2.”Start Learning”ボタンからスタート</h1>
青いボタン"Start Learning"をポチッと
<img width="400" alt="nextjs.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/69607/c3a43093-efd3-6782-9d1f-e6bbe3fe4995.png">

<h1>3.”Create a Next.js App”で、はじめにスタート</h1>
まずは、Next.jsとは：
<p><b>”Next.js: The React Framework”　Next.jsは、リアクトのフレームワーク</b></p>

(本当は、いい事いっぱい書いているのだけど、気になる人は公式サイトへ）

次に、<b>必要な環境は</b>：
<b>・Node.jsのバージョンは10.13かそれ以上</b>
<b>・お気に入りのテキストエディッタとターミナル系のアプリ</b>


準備ができたら、スタート！
1.ターミナル開いて、以下唱える

```terminal:terminal
npx create-next-app nextjs-blog --use-npm --example "https://github.com/vercel/next-learn-starter/tree/master/learn-starter"
```
2.nextjs-blogというディレクトリができているので、そちらへ移動（以下唱える）

```terminal:terminal
cd nextjs-blog
```
3.立ち上げるために、以下唱える（Next.jsを立ち上げるための言葉）

```terminal:terminal
npm run dev
```

4.確認のために、お気に入りのブラウザに、以下唱える

ローカルホストを開ける： http://localhost:3000 

<img width="400" alt="welcome.png]" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/69607/c1fafc3e-6c78-7d32-54d4-4c805e8f9f27.png">

完成（ぱちぱち！）

補足（編集してみましょう）：
・Next.js のサーバを立ち上げたままにしてください（npm run dev)
・pages/index.js を開きましょう
・h1タグの中の　“Welcome to”　を　“Learn”　に変えてみましょう
（保存を忘れずに）
<img width="400" alt="next_learn.png]" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/69607/24b9bf8b-3f12-771e-001f-a7efd315d67e.png">

編集完了

次は、ページ間の移動です。
Pythonで学ぶ制御工学　第2弾：制御モデルの例

# #Pythonで学ぶ制御工学< 制御モデルの例 >

##はじめに
基本的な制御工学をPythonで実装し，復習も兼ねて制御工学への理解をより深めることが目的である．
その第2弾として制御モデルの例を扱う．

##システム
システムには大きく分けて２つある．

**動的システム**
　　　　過去の状態に影響を受けるようなシステム

**静的システム**
　　　　過去の状態に依存しないようなシステム

制御対象は多くの場合，動的システムであり，ここで扱うのも動的システムである．


##制御モデル
制御を考えるためには，制御モデルを構築できなければならない．以下では，４つの例を示して，制御モデルとはどのようにして求められるのかということへの理解を深める．なお，図において，緑の背景で示したものが制御モデルである．

####制御モデル①：台車のモデル
次に台車と条件を示した図を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/ac134ffd-312f-11ef-495f-2fc8991df142.png)
以下にモデルの導出過程を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/a3184b23-cdd8-c60a-caa0-d8ab4dbd0126.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/47495806-58bf-2cf8-fbf4-076c892985df.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/9b1311c2-5b25-c9d2-d0c8-8acce9b2c2a8.png)


####制御モデル②：垂直駆動アームのモデル
次に垂直駆動アームと条件を示した図を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/21634f18-4f26-a63e-50bb-c4c5b49b1cfb.png)
以下にモデルの導出過程を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/0b5800b1-e785-793f-b7d1-bd728e4d92cd.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/b04245ab-b863-b2f8-ff88-bf0a8eba74e7.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/1c1a5bd6-e28c-8c70-2611-74001fd18d17.png)


####制御モデル③：RLC回路のモデル
次にRLC回路と条件を示した図を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/9d0a6d02-bb71-6083-458e-7646f996fe10.png)
以下にモデルの導出過程を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/fb206f96-0781-30db-8f75-10e72a854b11.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/196b089e-0d28-7da7-450e-7c281a53375e.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/49604a03-4d3c-5959-d474-1a849ddeec29.png)


####制御モデル④：増幅回路のモデル
次に増幅回路と条件を示した図を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/494c6faf-6d12-d2e3-55a6-cf6a887de868.png)
以下にモデルの導出過程を示す．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/666abdd9-28cd-ce48-e41a-dff7ccfeb203.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/dc885e0d-f4c2-9bf4-75f0-590e18b06ebf.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/951300/861aab66-a52c-daf9-9619-a6032e46592e.png)


##感想
久しぶりに制御モデルを求める手順をおさらいできた．次回からはようやく，これらの制御モデルに対して伝達関数などを扱うことができる．これについても学んできてはいるが，今回同様，良い復習になり，また新たな鬼月が得られるかもしれない．楽しみである．

##参考文献
Pyhtonによる制御工学入門　　南 祐樹　著　　オーム社
Rails6 herokuでデプロイ

# 初めまして
私は、オリアプを作成しており、そのうちの何個かはherokuでデプロイしています。
そこで、herokuでデプロイする方法を備忘録として残したいと思います。

# 環境
Rails6
Ruby2.6.5
# Herokuを操作します。


まだ、Herokuをインストールしていない方は、どのディレクトリでもいいので下記を実行しましょう。

```terminal
 % brew tap heroku/brew && brew install heroku
```
## Herokuへログインします。
まだ、Herokuの登録ができていない方は、先に登録してくださいね。

```terminal
# Herokuへログインするためのコマンド
% heroku login --interactive
  => Enter your Heroku credentials.
# メールアドレスを入力し、エンターキーを押す
  => Email:
# パスワードを入力して、エンターキーを押す
  => Password:

```

## Heroku上にアプリケーションを作成します。
自身のアプリのディレクトリに移動してください。そこで下記を実行します。

```terminal

% heroku create アプリ名

#git config --list | grep heroku作成できているか確認できます。

```
## Heroku上でDBを使えるようにします。
Heroku上のDBはデフォルトで「PostgreSQL」になっています。
なので、私はローカル環境で「Mysql」を使用していたのでDBの設定を変えます。

```terminal

% heroku addons:add cleardb
#ClearDbを追加することで「Mysql」を使用できます。

% heroku_cleardb=`heroku config:get CLEARDB_DATABASE_URL`
# ClearDBのURLを変数heroku_cleardbに格納します。。

% heroku config:set DATABASE_URL=mysql2${heroku_cleardb:5}
#DBのURLを再設定します。
```
## Heroku上にmaster.keyを設置します。
Heroku上にmaster.keyを環境変数として設置します。

```terminal

% EDITOR="vi" bin/rails credentials:edit
#credentials.yml.encをmaster.keyによって復号し、中身を確認しておきます。
# 「escキー」「:」「q」で閉じることが出来ます
```

```terminal
% heroku config:set RAILS_MASTER_KEY=`cat config/master.key`
# 本番環境へ設置します。
#heroku config で念のため設定できているか確認しておきます。
```

##アプリケーションをプッシュします。

Herokuで「Stack」を指定します。
※Stackはデプロイされたアプリケーションを読み取り正常に動作させるためのもの

今回私は「Ruby2.6.5」の為、「heroku-18」を使います。

```terminal

% heroku stack:set heroku-18 -a ご自身のアプリ名

% git push heroku master
# Herokuにプッシュします。

```

##　Heroku上にマイグレーションファイルを上げます。

Heroku上にもDBを反映させなければ正しく動作しませんので反映させます。

```terminal
% heroku run rails db:migrate

# heroku apps:infoでアプリの情報を見ることが出来ます。
```

上記の設定でアプリを公開することが出来ているはずです！

# Heroku上のアプリを削除したい場合
HerokuのWebサイトから削除することが出来ます。
手順として
①削除したアプリを選択
②「Settings」の一番下の「Delete」を押して、アプリ名を入力し削除

しかし、削除しただけでは全て消えません。
gitのリモートリポジトリにherokuが設定されたままになっています！
下記を実行します。

```terminal
% git remote rm heroku
```

# 最後に
herokuを使えば簡単にアプリケーションの公開ができるのでおすすめです！


ここまで読んでいただきありがとうございました！
A - Repeat ACL, B - Balance, C - Exam and Wizard

2021/2/12
くじかつ精進

##[A - Repeat ACL](https://atcoder.jp/contests/abl/tasks/abl_a)

O(1)

```python:python
N = int(input())
 
S = ""
for i in range(0, N):
  S += "ACL"
 
print(S)
```

##[B - Balance](https://atcoder.jp/contests/abc129/tasks/abc129_b)

O(N)

```python:python
import math
import itertools
 
N = int(input())
W = list(map(int, input().split()))
 
S1 = 0
S2 = sum(W)
res = 10000
for i in range(0, N):
    S1 += W[i]
    S2 -= W[i]
    res = min(res, abs(S2-S1))
        
print(res)
```

##[C - Exam and Wizard](https://atcoder.jp/contests/keyence2019/tasks/keyence2019_c)

O(N)

```python:python
N = int(input())
A = list(map(int, input().split()))
B = list(map(int, input().split()))
 
total = 0
total_BtoA = 0
total_AtoB = 0
total_AtoB_0 = 0
C = []
for i in range(0, N):
    if B[i] > A[i]:
        total_BtoA+=1
        total += B[i] - A[i]
    elif B[i] < A[i]:
        C.append(A[i] - B[i])
    else:
        total_AtoB_0 += 1
 
C.sort(reverse=True)
 
for i in range(0, len(C)):
    if total >=0:
        total -= C[i]
        total_AtoB+=1
 
if total>0:
    print(-1)
elif (len(C) + total_AtoB_0 == N):
    print(0)
else:
    print(total_AtoB + total_BtoA)
```
Unityの野球ゲームで簡単に変化球を実装する

Unityの野球ゲームで、投手に変化球を投げさせたい場合の簡易的な方法を書きました。

あくまで簡易的なので若干リアルさには欠けるかもしれません。

#手順
PlaneとSphereを用意します。
Sphereとカメラの距離はある程度空けておきます。
![653885a600eab7c7c73992f394624da7.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/774410/a5505f24-4e0d-762e-a009-ef60edb0ef85.png)

##ボールをど真ん中に投げてみる
まずはボールを真ん中に投げてみます。
SphereにRigidBodyコンポーネントを追加し、スクリプトは以下の通りで試してみます。
powerは1000ぐらい。

```c#:Ball.cs
public class BallTest : MonoBehaviour
{
    public Rigidbody _rb;
    public int power;
    Vector3 direction = Vector3.back;//カメラの方向に投げてみる

    void Start()
    {
        _rb.AddForce(direction * power);
    }
}
```
[![Image from Gyazo](https://i.gyazo.com/a0668779845adf66bb23fdc1c6de9d4b.gif)](https://gyazo.com/a0668779845adf66bb23fdc1c6de9d4b)
powerは丁度いいですが、球が転がってしまったので力を与える方向(direction)を修正します。

```
    Vector3 direction = new Vector3(0,0.2f,-1.0f);
```
[![Image from Gyazo](https://i.gyazo.com/d9f220e65ca91054f0d7589725e561bb.gif)](https://gyazo.com/d9f220e65ca91054f0d7589725e561bb)
これをど真ん中のストレートとします。

##球に変化を与える
飛ばした球がColliderに当たった際に変化方向に力を加えるという方法でいきます。
以下のように空のオブジェクトを作成しBoxColliderを追加。ボールの軌道の被るように配置します。
isTrrigerはONにします。
[![Image from Gyazo](https://i.gyazo.com/6366a3eabcda51b2f70c77a094964fcd.png)](https://gyazo.com/6366a3eabcda51b2f70c77a094964fcd)

最初はスライダーをかけてみます。
Sphereオブジェクトのtagは"Ball"に変更しておきます。

```c#:ChangeCollider.cs

    int changePower = 100; //変化させる力
    Vector3 sliderDirection = new Vector3(1.0f, -1.0f, 0); //変化の方向

    private void OnTriggerEnter(Collider other)
    {
        if (other.gameObject.tag == "Ball")
        {
            Rigidbody ball_rb = other.gameObject.GetComponent<Rigidbody>();
            ball_rb.AddForce(sliderDirection * changePower);//ボールに力を加える
        }
    }

```
<img width="400" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/774410/0a85bd76-6879-8e05-dd9a-051697821100.png">
[![Image from Gyazo](https://i.gyazo.com/a3200967282e93124880a8de7dd79937.gif)](https://gyazo.com/a3200967282e93124880a8de7dd79937)
なかなかいい感じですね。

Colliderの位置を前後させることで曲がり始めのタイミングをずらせます。
Z軸に力を加えるとブレーキをかけることもできます。

##様々な変化をさせてみた
せっかくなので投手を準備して色々な変化球を試してみました。
directionをいじれば様々な変化球を実現できます。
![ezgif.com-gif-maker.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/774410/b202973b-c05e-9763-2a4f-28c13a7e5466.gif)

投手のアセットはこちらを使用しました。

![1d589c9b7008af5afc597af6df96509e.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/774410/d2224b82-76c7-cfe0-f4df-5763ee39b0eb.png)
ES2015における{ClassName}構文についての解説

## ES2015における{ClassName}構文についての解説

１．前提知識となりますが、クラスとは、function型のインスタンスである。例として、任意のクラスClass01を定義し、typeof Class01を実行して戻り値が'function'であることをそれを証明します。補足の例として、下記構文を参考に。

```js
    // 下にあるClass01定義と同じクラス（constructor）を定義している
    let Class01 =
      class Class01 {
        p1: string = '';
     }

    class Class01 {
      p1: string = '';
    }
```

２．{ClassName}についての説明です、同じ効果を持つ二つの構文を参考に

```js
    // 下にある構文と同じ効果を持つ
    let v1 = { Class01 };

    let v1: { Class01: typeof Class01 } = {
      Class01: Class01  //プロパティClass01: function型の値Class01
    }
```

３．補足：Typeofオペレーターは実行時のみ働く仕様のようです。（同じfunctionなのにtypeof Class01 <> typeof Class02）


```js
    class Class02 {
      p2: string = '';
    }
    let v2: { Class01: typeof Class01 } = {
      Class01: Class02  //エラー：typeof Class01 !== typeof Class02
    }
```
【Ruby on Rails】返すデータに制限をかけたりかけなかったりするために、七つのアクション以外を定義するのはやめよう...

#なぜ書くか
これまたコードレビューの際にご指摘いただきました。
備忘録と、コツコツとプロの開発者としての思考を身につけるためにアウトプットさせていただきます。

#脱「動けばいい」精神
まず、前提としては、RailsはApiでのやり取り専用のコントローラ。
iOSアプリケーションからリクエストを受け取り、それぞれのリクエストに応じた処理が実行されます。

実際に問題となった機能を実装する前は、コントローラは下記の様な状態でした。（コードは多少変更しています。）

```ruby
module Api
  module V1
    class ProductController < ::Api::ApplicationController
      protect_from_forgery except: [:create]

      def index
        render json: Product.trader_filter(params[:trader_id])
      end

      def create
        render json: Product.new(product_params).save
      end

      private

      def product_params
        params.permit(:name, :price)
      end
    end
  end
end
```

しかしここでiOS側でのとあるページの都合で「その日、当日分の商品情報だけ欲しいな...」といったことが発生しました。（なんの当日分かは置いといて）
すかさず、Railsアプリケーションのコードを追加し、書いたコードは下記の様なコードです。

```ruby
module Api
  module V1
    class ProductController < ::Api::ApplicationController
      protect_from_forgery except: [:create]

      def index
        render json: Product.trader_filter(params[:trader_id])
      end

      def create
        render json: Product.new(product_params).save
      end

      def acquisition_of_product_data_on_the_day
        render json: Product.trader_release_date_filter(params[:trader_id], params[:release_date])
      end

      private

      def product_params
        params.permit(:name, :price)
      end
    end
  end
end
```

ルーティングにコレクションを使用し、七つのアクション以外のアクションを定義し、コントローラでモデルのスコープを呼び出しています。
この時は「もうindexは使っちゃってるしなぁ」と安直にアクションを追加し、これでいいと思っていました。

しかし、先輩にレビュー依頼出したところ、ここが指摘されました。

理由としては、検索条件を追加するたびにいちいちアクションを追加していたら、コントローラのメソッドの数がえげつないことになり、いわゆる「fat Controller」になってしまいメンテナンスが難しくなってしまうということでした。

まさに「動くからええやん...」気分で書いたコードでした。
しかし実際に本当にその通りで、検索の内容が変わるたびに「get」のリクエストを増やしまくっていたのでは、いつか維持できなくなります。
「将来的にも追加はそこまでないからいいのでは？」と思ったりもしたのですが、とにかく同じようなメソッドを何個もコントローラーに書くのはスマートではないと。

#ではどうするか？
本来コントローラは左から右へ処理、命令を流すだけの役割です。
なので、当日分のデータを返したいのかそうでないのか？といったこともコントローラに考えさせるべきではありません。

なのでindexで、全体取得、本日分のみの取得のリクエストも受け取り、モデルに判断させます。

```ruby
module Api
  module V1
    class ProductController < ::Api::ApplicationController
      protect_from_forgery except: [:create]

      def index
        render json: Product.trader_filter(params[:trader_id], params[:release_date])
      end

      def create
        render json: Product.new(product_params).save
      end

      private

      def product_params
        params.permit(:name, :price)
      end
    end
  end
end
```

最初との違いは、indexメソッドに渡すparamsの中身を追加しただけです。つまり取得したい日付のデータですね。

そしてモデルのスコープは以下のように実装します。

```ruby
scope :trader_filter, ->(trader_id, release_date) do
  if release_date.nil?
    #全件検索の処理
  else
    #当日分のデータ取得の処理
  end
end
```

これで、コントローラにアクションを増やすことなく、同じ動きを実現できました。
コントローラから、スコープを見に行くだけで、どのようなデータを返すようになっているかも一発で分かるので可読性もこちらの方が高いと思います。
15rep - 独自Errorの作成 ~ 備忘録

# 書いた理由
- API作成しているときにエラーって返すと思います。その際に独自でErrorを定義し返すというよくある内容をメモ化（作り込まず簡易）

# 独自エラーの定義
- 独自のエラー型を定義するやり方
- Goの組み込みのエラー型（error）は以下のような型です。
(errorインタフェース)

``` go
type error interface {
    Error() string
}
```
- func Error() string を実装した型は全てerrorインターフェースが実装されているものとみなす。（便利）

# 実際に書いてみた
``` go
package main

import (
	"fmt"
	"net/http"
	"encoding/json"
)

type ErrorMessage struct {
	Code    int
	Message string
}

// Errorメソッドさえ定義されていれば良い
func (e *ErrorMessage) Error() string {
	return e.Message
}

func errHandlerSample() error {
	return &ErrorMessage{
		Code: http.StatusBadRequest,
		Message: "sample error!!!",
	}
}

func main() {
	if err := errHandlerSample(); err != nil {
		switch err := err.(type) {
		case *ErrorMessage:
        // ErrorMessageの処理
        // switch文の頭で再定義したerr変数は*ErrorMessage型なので、
        // ErrorMessage型の各フィールドにアクセスできる。
          stJson := ErrorMessage{Code: err.Code, Message: err.Message}
          out, _ := json.Marshal(stJson)
          fmt.Println(string(out))
		default:
			fmt.Println("Hello, playground")
		}
	}
}

結果: {"Code":400,"Message":"sample error!!!"}
```
- 型キャストしSwitchで判定して出力しています。
- 他にも判別する内容があればStructで定義しSwitchの判定に入れてください。
- jsonで出力する部分は別途関数化して返す内容にしてもいいと思います。

``` go
func ResponseJSON(w http.ResponseWriter, obj interface{}, httpStatus int) error {
	b, err := json.Marshal(obj)
	if err != nil {
		return err.Error()
	}
	w.Header().Set("Content-Type", "application/json")
	w.Header().Set("Content-Length", fmt.Sprintf("%d", len(b)))
	w.WriteHeader(httpStatus)
	w.Write(b)
	return nil
}
```

# 終わりに
- 「func Error() string を実装した型は全てerrorインターフェースが実装されているものとみなす」　ので気軽に独自にError作成を作成できより状態に合わせて作成できます。

# 参考記事
[Go言語のエラーハンドリングについて](https://qiita.com/nayuneko/items/3c0b3c0de9e8b27c9548)
[WebAPIでエラーをどう表現すべき？15のサービスを調査してみた](https://qiita.com/suin/items/f7ac4de914e9f3f35884)
Pythonでフィボナッチ数の計算

#はじめに
僕がやりたいのはPythonでフィボナッチ数の計算をすることです
#実行環境
僕の実行環境です
Ubuntu:   20.04.2 LTS(64-bit)
Thonny:   3.2.7
Python:   3.8.5(64-bit)
#フィボナッチ数とは
フィボナッチ数をWikipediaで見てみると[[1]](https://ja.wikipedia.org/wiki/%E3%83%95%E3%82%A3%E3%83%9C%E3%83%8A%E3%83%83%E3%83%81%E6%95%B0)、

>概要
>フィボナッチ数列（フィボナッチすうれつ、（英: Fibonacci sequence） ($F_n$) は、次の漸化式で定義される：

```math
F_0 = 0,\\
F_1 = 1,\\
F_{n+2} = F_n + F_{n+1} (n ≥ 0)\\
```

>第0～21項の値は次の通りである：
>0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610, 987, 1597, 2584, 4181, 6765, 10946, …（オンライン整数列大辞典の数列 A000045）
>1202年にフィボナッチが発行した『算盤の書』(Liber Abaci) に記載されたことで「フィボナッチ数」と呼ばれているが、それ以前にもインドの学者であるヘーマチャンドラ (Hemachandra) が韻律 の研究により発見し、書物に記したことが判明している。

とありますが、簡単に言うと

1,1,2,3,5,8,13,21,34,55,89,144,etc･･･

のように、前の数とその前の数を足していった数のことです


#スクリプト
前の数をa、前の前の数をbとすると、

```python
total_num = 0
a = 1
b = 1
e = 8
while e != 0:
    print(str(total_num)+','+str(a),end=',')
    total_num += a
    a += b
    b += a
    e -= 1
print('etc・・・')
#0,1,1,2,3,5,8,13,21,34,55,89,144,233,377,610,etc・・・
```

total_numとaがフィボナッチ数として出力されます
eの部分を変えれば出てくるフィボナッチ数が増えたり減ったりします


#最後に
間違っている点や改善出来るところがあればコメント欄でお知らせください
よろしくお願いします

[1:Wikipedia](https://ja.wikipedia.org/wiki/%E3%83%95%E3%82%A3%E3%83%9C%E3%83%8A%E3%83%83%E3%83%81%E6%95%B0)
Docker+nginx+Laravel7環境構築メモ

# DockerでLaravel環境構築
自作ツールの環境の理解を深めたく(というかネットからクローンしてきて理解してなさすぎたので)
環境構築し直したときの自分用メモです。

## 環境構築
Laravel7
PHP/nginx/MySQL

下記の記事を参考に構築。
https://qiita.com/A-Kira/items/1c55ef689c0f91420e81

``` :作業メモ

// DBの準備
php artisan migrate

// 認証機能の追加
https://readouble.com/laravel/7.x/ja/frontend.html
composer require laravel/ui:^2.4
php artisan ui:auth

// bootstrapの導入
php artisan ui bootstrap --auth 

// CSSの出力(package.jsonがあるところで実行)
npm install && npm run dev
```

## 詰まったメモ１：mysqlコマンドが実行できない
```
SQLSTATE[HY000] [1045] Access denied for user 'user名'@'172.-.-.-' (using password: YES)
```
####  解決：キャッシュクリアコマンド実行
```
php artisan cache:clear
php artisan config:cache
```
参考：https://shiro-changelife.com/laravel-access-denied/



## 詰まったメモ２：CSS/js反映されない
Laravelの表示画面はいい感じ(？)に表示されるが、ログイン／登録画面以降はCSSやらjsが反映されていない。
キャッシュはクリアしたし、css/jsはちゃんとpublic下にある。

<img width="50%" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/697384/d8e0cad9-becd-48cd-6f22-70a6a819d702.png">
<img width="50%" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/697384/5a59cb6b-da59-24ec-0e39-9326d8d84814.png">

コンソールを見るとCSSとJSがNotFoundになっている
``net::ERR_ABORTED 404 (Not Found)``
![スクリーンショット 2021-02-13 17.13.59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/697384/88c0924a-4180-262d-6def-71fedc6146d4.png)

#### 解決：``nginx/default.conf``に記載しているrootの指定が誤っていた
```
server {
  listen 80;
    index index.php index.html;
    root /var/www/{サービス名}/public; ←ココは変えてたけど

  location / {
    root /var/www/{サービス名}/public; ←ココを変えてなかった
    index  index.html index.php;
    try_files $uri $uri/ /index.php$query_string;
    }
```




## その他メモ
ブルーライトカットメガネ忘れて１日PCに向かったら目が死んだ。
自分のブルーライト耐性無くなってて引いた


来月のデブキャンまでにはこのツール完成させたい。。。
Cron + Pythonの覚え書き

# cronの基本
## 編集方法と起動確認
```sh
$ sudo systemctl status cron
● cron.service - Regular background program processing daemon
     Loaded: loaded (/lib/systemd/system/cron.service; enabled; vendor preset: enabled)
     Active: active (running) since Sat 2021-02-13 19:03:03 JST; 3min 32s ago
       Docs: man:cron(8)
   Main PID: 352260 (cron)
      Tasks: 1 (limit: 9386)
     Memory: 436.0K
     CGroup: /system.slice/cron.service
             └─352260 /usr/sbin/cron -f

$ crontab -e
```
## 書式
`分 時 日 月 曜 コマンド`となる

### 例 (シェルスクリプトの実行)
- 毎日10時に実行

```sh
0 10 * * * test.sh
```

- 毎月1日の0時0分に実行

```sh
0 0 1 * * test.sh
```

- 1時間おきに実行(毎時0分)

```sh
* */1 * * * test.sh
```

- 毎週土曜日の20時に実行

```sh
* 20 * * 6 test.sh
```
**日曜日が0、土曜日が6と定義されており[0-6]の数値で指定する**

## 適用
```sh
sudo systemctl restart cron
```

# Pythonの実行
## Pathの設定
　cronではパスの設定がされていないため、Pythonを絶対パスで指定するかPathを通す必要がある
　他のコマンドも同様であることを考えるとPathの設定をするのが無難
　`crontab -e`で編集モードに入り、最初の行に以下を追記する

```sh
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin
```

## Python内で相対パスを使用している場合
　実行位置が違うため、カレントディレクトリを修正する必要がある。

### サンプル
- `.env`ファイルを作成し、カレントディレクトリを記述する

```.env
CWD = '/home/hoge/hogehoge'
```

- `config.py`を作成し、環境変数の読み込みを行う

```config.py
import os
from dotenv import find_dotenv, load_dotenv

load_dotenv(find_dotenv())
CWD = os.environ.get('CWD')
```

- メインのファイルで `config.py`を読み込み、環境変数を利用する

```main.py
import os
import config

os.chdir(config.CWD)  # カレントディレクトリの変更
print(os.getcwd())    # カレントディレクトリの確認
```
Laradock使い方手順

初めてlaradockを使い環境構築を行ったのでその手順をメモ

任意のディレクトリを作成しlaradockをクローンしてくる。

```
% git clone https://github.com/LaraDock/laradock.git
```
envをコピー

```
% cp env-example .env
```

コンテナの起動

```
% docker-compose up -d nginx mysql workspace
```
ここでlocalhost上にサーバが立ち上がり、404エラーが表示されます。

workspaceに移動

```
docker-compose exec --user=laradock workspace bash
```

laravelをインストール(ここではVersion7を指定)

```
composer create-project --prefer-dist laravel/laravel laravel '7.*'
```
laradockのenvのAPP_CODE_PATH_HOSTを上記で作成したフォルダ名に書き換える

```
APP_CODE_PATH_HOST=../laravel/
```

dockerを再起動する

```
docker-compose stop
```

```
docker-compose up -d nginx mysql workspace
```

ブラウザでlocalhostを開く
![スクリーンショット 2021-02-13 19.00.08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/429828/7e3e00da-9c09-4dc9-4cde-e9fb83c62751.png)

##MySQLの設定をおこなう

laravelの.env内の環境変数を変更

```
DB_CONNECTION=mysql
DB_HOST=mysql
DB_PORT=3306
DB_DATABASE=default
DB_USERNAME=default
DB_PASSWORD=secret
```

マイグレーションを実行
docker-compose exec --user=laradock workspace bash　のコマンドを打った/var/www# 上で行うことに要注意

```
php artisan migrate
```
マイグレーションができれば完了です。

参考
https://reffect.co.jp/laravel/laradock-laravel-macos
https://qiita.com/tdkn/items/b8aa24cca0ba2904f8e7
Go 言語仕様6（goroutine 並行処理）

## 概要
Go 言語の仕様まとめ。

前回：
[Go 言語仕様5（スライス、マップ）](https://qiita.com/R_R/items/3c9047811c78c916bef3)

## 内容

- goroutine 並行処理

## goroutine 並行処理

以下のようにループ処理が2つある場合、プログラムは上から下に実行されるため、
SubLoop関数のループ処理が完了後しないと、main関数のループ処理が実行されない。

```GO
func SubLoop() {
	for i := 0; i < 20; i++ {
		fmt.Println("SubLoop:", i)
	}
}

func main() {
	SubLoop()

	for i := 0; i < 20; i++ {
		fmt.Println("MainLoop:", i)
	}
}
```

```GO:実行結果
SubLoop: 0
SubLoop: 1
SubLoop: 2
SubLoop: 3
SubLoop: 4
SubLoop: 5
SubLoop: 6
SubLoop: 7
SubLoop: 8
SubLoop: 9
MainLoop: 0
MainLoop: 1
MainLoop: 2
MainLoop: 3
MainLoop: 4
MainLoop: 5
MainLoop: 6
MainLoop: 7
MainLoop: 8
MainLoop: 9
```

goroutineを使うことで、2つのループ処理を並行して走らせることができる。
以下のように SubLoop( ) の前に go と記述するだけ。

```GO
func SubLoop() {
	for i := 0; i < 20; i++ {
		fmt.Println("SubLoop:", i)
		// 実行結果がわかりやすいようにsleepを入れておく
		time.Sleep(100 * time.Millisecond)
	}
}

func main() {
	go SubLoop()

	for i := 0; i < 20; i++ {
		fmt.Println("MainLoop:", i)
		time.Sleep(200 * time.Millisecond)
	}
}
```

```GO:実行結果
MainLoop: 0
SubLoop: 0
SubLoop: 1
MainLoop: 1
SubLoop: 2
SubLoop: 3
MainLoop: 2
SubLoop: 4
SubLoop: 5
MainLoop: 3
SubLoop: 6
SubLoop: 7
MainLoop: 4
SubLoop: 8
SubLoop: 9
MainLoop: 5
MainLoop: 6
MainLoop: 7
MainLoop: 8
MainLoop: 9
```

## 次回

[Go 言語仕様7（goroutine と channel）]()
dockerで形態素解析の環境構築（jupyter + mecab）

# はじめに
docker-composeを用いて、手軽に形態素解析の実行環境を構築する手順を整理した。（処理フローは下図。）
![docker_arch.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/329863/202e7064-f23a-efe3-7a45-76b72edf44a9.png)

# 本手順のメリット
1. コンテナによるポータブルな環境構築が可能である。 
2. [作成済のイメージ](https://hub.docker.com/search?q=mecab&type=image)では把握しづらい内部処理を理解できる。

# 準備するもの
作業ディレクトリに、下記の3ファイルを作成する。

```bash:ローカルPC
作業ディレクトリ
├─ Dockerfile
├─ requirements.txt
└─ docker-compose.yml
```

```dockerfile:Dockerfile
FROM jupyter/base-notebook

USER root
RUN apt-get update && apt-get install -y \
  make \
  curl \
  file \
  git \
  libmecab-dev \
  mecab \
  mecab-ipadic-utf8

RUN git clone --depth 1 https://github.com/neologd/mecab-ipadic-neologd.git
RUN mecab-ipadic-neologd/bin/install-mecab-ipadic-neologd -y

COPY requirements.txt $PWD
RUN pip install -r requirements.txt
```


```requirements.txt
mecab-python3
```

```docker-compose.yml
version: "3.7"
services:
  jupyter-notebook:
    image: mecab-base-notebook
    container_name: mecab-notebook
    build:
      context: .
      dockerfile: Dockerfile
    ports:
      - "889:8888"
    volumes:
      - ./work:/home/jovyan/work
```

今回は[base-notebook](https://hub.docker.com/r/jupyter/base-notebook)を利用した。jupyterの公式で[軽量のイメージ](https://jupyter-docker-stacks.readthedocs.io/en/latest/using/selecting.html#image-relationships)になる。
また、[mecab実行に必要なライブラリ](https://github.com/neologd/mecab-ipadic-neologd#examples)とPythonのPackageはDockerfileで管理する構成にしている。

# 環境構築
下記の1コマンドで『Dockerイメージの作成＆Dockerコンテナの作成・起動』を行う。
```Creating mecab-notebook ... done```と標準出力されれば、環境構築に成功。
また、ローカルPCには「workフォルダ」が作成され、構築環境と同期されている。

```bash:bash
> docker-compose up -d --build
```

# 構築環境にアクセス
構築環境(jupyter notebook)のURLは「[http://localhost:889/tree/work](http://localhost:889/tree/work)」となる。
初回アクセス時は「Password or token」を要するため、稼働中のコンテナからtokenを取得する。

```bash:bash
> docker exec -it mecab-notebook jupyter notebook list
http://0.0.0.0:8888/?token=xxxxxxxxxxx :: /home/jovyan
```

# 形態素解析の動作確認
構築環境にアクセスし、形態素解析が問題なく実行されていることを確認。
[mecab-ipadic-NEologd](https://github.com/neologd/mecab-ipadic-neologd/blob/master/README.ja.md)を利用するため、新語(ONE TEAM など)の形態素解析が可能となる。
![mecab_python.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/329863/88d610b1-4736-5419-c4fa-a08a0e693c9d.png)

```python:コピー用
import MeCab

MECAB_SETTING = "/etc/mecabrc"
MECAB_DICTIONARY = "/usr/lib/x86_64-linux-gnu/mecab/dic/mecab-ipadic-neologd"
MECAB_ARGS = " -r " + MECAB_SETTING + " -d " + MECAB_DICTIONARY

m = MeCab.Tagger(MECAB_ARGS)

text = "ONE TEAMは１日にして成らず"
print(m.parse(text))
```
※neologdのパスは```docker exec -it mecab-notebook mecab-config --dicdir``` で確認可能。

# おわりに
自然言語処理などで利用される形態素解析の実行環境を構築した。
Dockerコンテナを作成済のため、以降は[コンテナの起動・停止コマンド](https://qiita.com/rasyo/items/dd6f8dfc422511da25d6#%E5%AD%A6%E7%BF%92%E7%92%B0%E5%A2%83%E3%81%AE%E5%81%9C%E6%AD%A2%E8%B5%B7%E5%8B%95)で、環境の起動・停止が可能となる。
ターミナル上でローカルサーバーを動かせなくなったとき

rubyメモ

``Address already in use - bind(2) for "127.0.0.1" port 3000 (Errno::EADDRINUSE)``
というポート3000がすでに使われているというエラーがターミナル上で出現した。

原因はよくわかっていない。

``%lsof -i:3000``
でポート３０００を使用しているプロセスを発見。

``
ruby    61207 nakagawasoma   11u  IPv6 0x16e108863b855d9d      0t0  TCP localhost:hbci (LISTEN)
ruby    61207 nakagawasoma   12u  IPv4 0x16e108864520de8d      0t0  TCP localhost:hbci (LISTEN)
ruby    61207 nakagawasoma   17u  IPv6 0x16e10886446ae3fd      0t0  TCP localhost:hbci->localhost:61780 (CLOSE_WAIT)
ruby    61207 nakagawasoma   18u  IPv6 0x16e10886446af0bd      0t0  TCP localhost:hbci->localhost:61778 (CLOSE_WAIT)
``
killコマンドを使い実行中のプロセスを削除

``%kill -9 61207``
lsof -i:3000でもう一度確認し、完了。
【Python】comment属性でセルのコメントを取得する

pythonを使用してExcelファイルの操作を勉強しています。
本日の気づき(復習)は、セルのコメントに関してです。
pythonでExcelを操作するため、openpyxlというパッケージを使用しています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/927441/ac37dd9c-0990-be41-1383-9062d207cb36.png)

上記のような各コメントを一覧で残しておきたいとします。

# セルのコメントを取得する方法
先ずはセルにコメントがあるかどうかの判定をします

```python
# セルにコメントがあるかどうかを判定
cell.comment
# コメントがない場合
--> None
```

コメントがあったら、下記のように取得します。

```python
# コメントのテキストを取得
cell.comment.text

# コメントの作成者を取得
cell.comment.aouther
```

コメントを挿入することもできます。

```python
# コメントのテキストを取得
cell.comment = Comment(コメントのテキスト,コメントの作成者)
```

コメントが挿入されている番地を取得する事も出来ます。

```python
# コメントが挿入されているセル番地を取得
cell.coordinate
```

# Worksheet.iter_rowsメソッド
今回はセルの1行目から順にコメントの有無を調べたいので、
Worksheet.iter_rowsメソッドを使用しました。

```python
ws.iter_rows(min_row=最小の行番号,max_row=最大の行番号,
             min_col=最小の列番号,max_col=最大の列番号)
```

max_rowなどの引数を省略するとデータが入っている最大の位置まで取得してくれます。

ちなみに、rowsがあったら、colsもやっぱりあって

```python
ws.iter_cols(min_col=最小の列番号,max_col=最大の列番号,
             min_row=最小の行番号,max_row=最大の行番号)
```

こちらで、列単位で順に取得してくれます。
これらをふまえて

```python:read_comment.py
from openpyxl import load_workbook, Workbook
from openpyxl.comments import Comment

wb_new = Workbook()
ws_new = wb_new.active
ws_new.title = '説明一覧'

wb = load_workbook('日報.xlsx')
ws = wb.active

ws_new['B2'] = '説明内容'
ws_new['C2'] = '記入者'
ws_new['D2'] = 'セル番地'
ws_new.column_dimensions['B'].width = 40
row_count = ws_new.max_row
print(f'新規作成したシートの行数は{row_count}です。')

for row in ws.iter_rows(min_row=1):
    for cell in row:
        if cell.comment is None:
            continue
        row_count = row_count + 1
        ws_new[f'B{row_count}'] = cell.comment.text
        ws_new[f'C{row_count}'] = cell.comment.author
        ws_new[f'D{row_count}'] = cell.coordinate

ws_new['D2'].comment = Comment('説明があったセル番号', 'hogehoge')
wb_new.save('説明一覧.xlsx')
```

こんな感じで記述してみました。
個人的にはコメント取得よりも、Worksheet.iter_rowsメソッドの方が勉強になりました。
laravel6でS3に画像アップロード&削除

#S3に画像をアップロードする方法

[LaravelでAWS S3へ画像をアップロードする](https://qiita.com/nobu0717/items/51dfcecda90d3c5958b8)
こちらの記事を参考にして無事S3に画像を保存できました

#S3の画像の削除
※先程の記事の一部を引用し、削除コードを書いていきます
参考記事のコード = `PostsController.php`
実装コード　= `exampleController.php`

削除ボタンを押すと、このコントローラが走るようにルーティング


```exampleController.php
public function delete(Request $request) {
        $image = $request->image_path;
        $s3_delete = Storage::disk('s3')->delete($image);
        $db_delete = Post::where('image',$image)->delete();
        return redirect('hogehoge');
    }
```

これでDBとS3から画像を削除！
とおもいきや、Dbからは削除されるのにS3からは削除できていない

## S3から削除できない原因

```PostsController.php
$post->image_path = Storage::disk('s3')->url($path);
```

参考記事ではこのように、パスにURL関数を使いそれをDBに保存しているので、DBにはURLを含んだパスが保存されています。

S3は`vi3kAwK0z0X19XU3LWcz63101t0rYilRHiWG9MmC.jpg`

DBは`https://example.s3-ap-northeast-1.amazonaws.com/myprefix/vi3kAwK0z0X19XU3LWcz63101t0rYilRHiWG9MmC.jpg`
のように保存されているため、
`exampleController.php`の`$image`はこうなっています。

```exampleController.php

$image = https://example.s3-ap-northeast-1.amazonaws.com/myprefix/vi3kAwK0z0X19XU3LWcz63101t0rYilRHiWG9MmC.jpg;
```
なのでS3に「そんなものないよ！」と言われているので削除ができないということでした。

##解決策
参考記事をこのように変更します。

```PostsController.php
public function create(Request $request)
  {
      $post = new Post;
      $form = $request->all();

      //s3アップロード開始
      $image = $request->file('image');
      // バケットの`myprefix`フォルダへアップロード
      $path = Storage::disk('s3')->putFile('myprefix', $image, 'public');
      // アップロードした画像のフルパスを取得
+     $post->image_path = $path; //追加
-     $post->image_path = Storage::disk('s3')->url($path); //削除

      $post->save();

      return redirect('posts/create');
  }
```

こうすることで、S3とDBに保存される名前を一致できたので`exampleController.php`を内容は変更せず削除ができるようになりました。

#View
srcに`https://example.s3-ap-northeast-1.amazonaws.com/`を追加すると表示することができました!

```
<img src="https://example.s3-ap-northeast-1.amazonaws.com/{{ $my_image['image'] }}" >
```

#参考
[LaravelでAWS S3へ画像をアップロードする](https://qiita.com/nobu0717/items/51dfcecda90d3c5958b8)
[LaravelでS3のファイル操作をする方法まとめ](https://sagatto.com/20190130_laravel_s3_file_operation)
[Rails]gretelとパンくず（パンくずリストの作り方）

# 何を書くのか
railsのgem "gretel"を用いたパンくずリストの作り方

## 環境
Rails: 6.0.3.4
Ruby: 2.6.5

## 結論
gretelの力でパンくずを作成し、それをビューで表示する。

## パンくずリストとは
![スクリーンショット 2021-02-13 午後6.34.56.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/948673/5c2e7b41-7b46-8e9f-df2f-a186b2b20577.png)

こういう風に、ヘッダーなどに「今どこどこにいますよ！」っていう表示を見た事があるでしょうか。これを**パンくずリスト**と言います。今回は、これを作成していきます。

## gretelの導入
今回使うのは、gemのgretelです。
[gretelのGithub](https://github.com/kzkn/gretel)

最初に、gretelの導入を行います。

Gemfileに記述し、bundle installします。

```Gemfile
gem "gretel"
```
と、記述し、ターミナルで

```
$ bundle install
```

を実行します。

そしたらターミナルでこちらのコマンドを実行しましょう。

```
rails g gretel:install
```

これを実行すると、"breadcrumbs.rb"というファイルが生成されます。
ファイルの中は、こんな感じになっているかと思います。

```breadcrumbs.rb
crumb :root do
  link "Home", root_path
end

# crumb :projects do
#   link "Projects", projects_path
# end

# crumb :project do |project|
#   link project.name, project_path(project)
#   parent :projects
# end

# crumb :project_issues do |project|
#   link "Issues", project_issues_path(project)
#   parent :project, project
# end

# crumb :issue do |issue|
#   link issue.title, issue_path(issue)
#   parent :project_issues, issue.project
# end

# If you want to split your breadcrumbs configuration over multiple files, you
# can create a folder named `config/breadcrumbs` and put your configuration
# files there. All *.rb files (e.g. `frontend.rb` or `products.rb`) in that
# folder are loaded and reloaded automatically when you change them, just like
# this file (`config/breadcrumbs.rb`).

```
これが確認できれば、準備は完了です。

## breadcrumbs.rbの中身を作る
それでは、ここからはパンくずリストの中身、つまり表示する文字列だったりを決めます。
ここでは、gretelの公式で紹介されている例を参考に説明します。

```breadcrumbs.rb
#トップページ
crumb :root do
  link "Home", root_path
end

# 一覧表示ページ
crumb :issues do
  link "All issues", issues_path
end

# 詳細表示ページ
crumb :issue do |issue|
  link issue.title, issue
  parent :issues
end

```

説明を加えます。

```breadcrumbs.rb
link "Home", root_path
```
基本の型は、'link "表示する文字列", パス'です。それを

```breadcrumbs.rb
crumb :root do
  link "Home", root_path
end
```
のように、do~endで囲ってあげます。
ちなみに、:rootは、ビューの表示等で利用することになるので、自分が判断しやすい名称に設定しておきましょう。

また、こういうこともできます。

```breadcrumbs.rb
#詳細表示ページ
crumb :issue do |issue|
  link issue.title, issue
  parent :issues
end

```

詳細表示ページには、parent :issuesとあります。これは、「issuesを親に持つよ！」ということを示しています。
これがないと、ページ間のつながりを判断してもらえず、意味がなくなってしまいます。

## ビューに表示する
それでは、先ほど作ったパンくずリストの要素等を、ビューで表示していきます。

この例では、app/views/issues/show.html.erbを例にだします。

```issues/show.html.erb
<% breadcrumbs :issue, @issue> 
<%= breadcrumbs separator: " &rsaquo; " %>  <%# 矢印を示すオプション　%>
```
基本的に、表示に必要なのは、この二つだけです。１行目で、（コントローラーから送られてきた）@issueを、先ほどcrumbの後ろにシンボルで記述した:issueのバリューとして定義します。あとは、自由にオプションをつけて、完成です。

## 補足
これは、初歩中の初歩です。[公式Github](https://github.com/kzkn/gretel)にはいろいろなオプションが確認できるので、ここからはそちらを参考してください。

#最後に
最後まで読んでいただき、ありがとうございます。
ソースコード、記事の書き方について**「もっとこうしたほうがいいよ！」というご意見、「そこどうなっているの？」というご質問**など、お待ちしております。

#参考文献
[gretel](https://github.com/kzkn/gretel)
Go 言語仕様4（defer, panic, recover）

## 概要
Go言語の仕様をまとめる。

前回：
[Go 言語仕様3（エラーハンドリング、for文、型アサーション、switch文、型スイッチ）](https://qiita.com/R_R/items/30d85996de24c00ba79d)

## 内容

- defer
- panic
- recover

## defer

- 関数の終了時に実行する処理を登録できる。

```GO
func Defer() {
	// STARTのPrint関数が実行された後に、deferで定義したENDのPrint関数が実行される
	defer fmt.Println("END")
	fmt.Println("START")
}

func main() {
	Defer() // START END
}
```

- 無名関数を使えば、複数登録可能。

```GO
defer func() {
	fmt.Println("A")
	fmt.Println("B")
	fmt.Println("C")
}()
```

- deferを複数定義すると、後から定義したdeferから実行される

```GO
func Defers() {
	defer fmt.Println("A")
	defer fmt.Println("B")
	defer fmt.Println("C")
}

func main() {
	Defers() // C B A
}
```

- 以下のようなリソースの開放での使用用途が多そう

```GO
func main() {
	// ファイルを作成して
	file, _ := os.Create("test.txt")
	// Close関数の実行を登録しておいて
	defer file.Close()
	// ファイルに文字列を書き込む
	file.Write([]byte("Golang"))
}
```

## panic

runtime errorを発生させ、実行中のプログラムを強制的に終了させる。
なお、deferで定義しておいた処理は実行される。

以下の例だと"START"は出力されない。

```GO
func main() {
	defer fmt.Println("END")
	panic("PANIC")
	fmt.Println("START")
}
```

## recover

panicを使用する場合、defer + recoverで処理方法を書いておく。
recoverを使うことで、panicの内容を取得でき、プロセスの強制終了も回避できる。

```GO
func main() {
	defer func() {
		fmt.Println("END")
		if err := recover(); err != nil {
			fmt.Println("Error:", err) // Error: runtime error
		}
	}()

	fmt.Println("START")

	panic("runtime error")
}
```

## 次回
[Go 言語仕様5（スライス、マップ）](https://qiita.com/R_R/items/3c9047811c78c916bef3)
コマンドラインから Arduino のプロジェクト作成とアップロードを行う ( Arduino-cli )

コマンドラインから Arduino のプロジェクト作成とアップロードを行います。

うまくすれば、github に上がっているものをそのまま流し込むとかできるようになるかと思います。

動作環境

項目|設定値
---|---
ボード|Arudino nano
ブートローダ|old bootloader

Arudino nano ( old bootloader ) 向けのコマンドラインでのスケッチアップロードです。

ターミナルにコピペでいけるかと思います。

```bash:install-arduino-cli.sh
#!/usr/bin/bash

# bash install-arduino-cli.sh ;

# arduino-cli install
curl -fsSL https://raw.githubusercontent.com/arduino/arduino-cli/master/install.sh | sh ;
echo export PATH='$HOME/bin:$PATH' >> ~/.bashrc ; # 環境変数の追加
source .bashrc ; # 環境変数の有効化
arduino-cli ; # 動作確認

# board update
arduino-cli core update-index ;
arduino-cli core install arduino:avr ;
arduino-cli board listall ;
arduino-cli board list ;

# create project
arduino-cli sketch new MyFirstSketch ;
HOGE=$(cat<<TEXT
void setup() {
    pinMode(LED_BUILTIN, OUTPUT);
}
void loop() {
    digitalWrite(LED_BUILTIN, HIGH);
    delay(100);
    digitalWrite(LED_BUILTIN, LOW);
    delay(100);
}
TEXT
) ;
echo "$HOGE" > MyFirstSketch/MyFirstSketch.ino ;

# compile and update
arduino-cli compile --fqbn arduino:avr:nano MyFirstSketch/MyFirstSketch.ino ;
arduino-cli upload -p /dev/ttyUSB0 -b arduino:avr:nano:cpu=atmega328old MyFirstSketch ; # sudo chmod 777 /dev/ttyUSB0 :-)
# arduino-cli upload -p /dev/ttyUSB0 -b arduino:avr:uno MyFirstSketch ; # sudo chmod 777 /dev/ttyUSB0 :-)
````

###参考リンク
- [arduino-cli初期設定(内蔵LEDでLチカ) - Life with IT ](https://l-w-i.net/t/arduino/cli_001.txt)
- [Installation - Arduino CLI ](https://arduino.github.io/arduino-cli/latest/installation/)
- [Getting Started with arduino-cli - Arduino Project Hub ](https://create.arduino.cc/projecthub/B45i/getting-started-with-arduino-cli-7652a5)
- [support to ATmega328P (Old Bootloader) · Issue #538 · arduino/arduino-cli ](https://github.com/arduino/arduino-cli/issues/538)
Big Surにアップデート後、Google Meetが使えなくなった場合の対処法

## はじめに
macOSをBig Surにアップデートした後、Google Meetで相手からの映像、音声が全く届かなくなってしまい、しばらくGoogle Meetを使うときのみ別のPCを使用していたのですが、ようやく原因および対処法がわかりましたので、紹介したいと思います。事象としては、[Big Sur Google Meet Bug (YouTube)](https://www.youtube.com/watch?v=6x2gCkL6SDA) が分かりやすいと思います。

## 確認環境
- macOS Big Sur (11.2.1)
- Google Chrome (88.0.4324.150)
- Safari (14.0.3)
- Firefox (85.0.1)

## 原因
以下の条件が重なった場合にこの不具合が再現します。

- macOSがBig Surである
- ブラウザがGoogle Chrome、もしくはSafariである
- 有線LANでインターネット接続してる

## 対処法
対処法としては、以下の3つで解消することを確認しています。

- IPv6の設定をリンクローカルのみにする
- インターネット接続を有線LANからWifiに切り替える
- Chrome/Safariではなく、Firefoxを使用する
 
### IPv6の設定をリンクローカルのみに設定するには
「システム環境設定」→「ネットワーク」→「USB 10/100/1000 LAN」を選択し「詳細」をクリックします。「TCP/IP」タブにある、「IPv6の設定」を「リンクローカルのみ」に変更し、「OK」をクリックします。その後、「適用」をクリックすることで設定が反映されます。

## 参考
- [Big Sur Google Meet Bug (YouTube)](https://www.youtube.com/watch?v=6x2gCkL6SDA)
- [Google Hangout / Meet not working with ethernet cable on Macbook 2020](https://stackoverflow.com/questions/65561109/google-hangout-meet-not-working-with-ethernet-cable-on-macbook-2020)
【Vue.js】vue3でlodash入れた時のエラー

#lodashインストール時のエラー
[lodashの公式ページ](https://www.npmjs.com/package/vue-lodash)通りやって、__yarn serve__してみたところ

```
npm install --save vue-lodash lodash
```

__エラー__が出た。

```
Error: Cannot find module 'vue-loader-v16/package.json'
Require stack:
- /Users/kiratanaka/Vue/MyCreate/portfolio/node_modules/@vue/cli-service/lib/config/base.js
- /Users/kiratanaka/Vue/MyCreate/portfolio/node_modules/@vue/cli-service/lib/Service.js
- /Users/kiratanaka/Vue/MyCreate/portfolio/node_modules/@vue/cli-service/bin/vue-cli-service.js
Error: Cannot find module 'vue-loader-v16/package.json'
```

これしたらいいんじゃない？と言われるけど、__無駄__。

```
npm i --save-dev vue-loader-v16
```

#解決

__[このページ](https://www.samanthaming.com/journal/3-how-to-use-lodash-with-vue/)__に助けられた。

```
yarn add lodash
```

__これだけ__。
【Express】静的ファイルをホスティングする方法

#プログラミング勉強日記
2021年2月13日
静的ファイルのホスティングをする方法を間違えていたため、以下のようなエラーが出た。

```
net::ERR_ABORTED 404 (Not Found)
```


#Expressで静的ファイルをホスティングする方法
　Expressで、　画像、CSSファイル、JSファイルなどの静的ファイルをホスティングするためには標準で組み込まれている`express.static`を使用する。

```js:関数のシグネチャ
express.static(root, [options])
```

　`express.static`の基本的な使い方は、Applicationオブジェクトの`use()`を使ってミドルウェアの設定を行う。

```:ファイルの構造
app.js
public/
    +-- images/
    +-- js/
    +-- css/
```

```js:app.js
app.use(express.static(__dirname + '/public'));
```


```js:app.jsの全体のコード
var express = require('express');
var app = express();

app.use(express.static('public', { hidden: true }));
app.listen(process.env.PORT || 7000);
```

#参考文献
[Serving static files in Express](https://expressjs.com/en/starter/static-files.html)
[javascript - JSファイルはnet::ERR_ABORTED 404(Not Found)を取得します](https://ja.ojit.com/so/javascript/1242604)
【Godot】スクリプトだけで文字を描画する方法

# 概要
この記事では、`Label` などを使用せずにスクリプトだけで文字を描画する方法について書きます。

# デフォルトフォントを使用した描画
スクリプトだけで文字の描画を行う場合は、`_draw()` 内で、`draw_string()` を呼び出します。

以下、サンプルコードです。

```gd
extends Node2D

var font:BitmapFont

func _ready():
	# デフォルトフォントを取得
	font = Control.new().get_font("font")
	
func _process(delta):
	# 描画情報に変更がある場合は update() を呼び出して更新する必要がある
	# 更新しない場合は update() の呼び出しは不要
	update()

func _draw():
	# デフォルトフォントを使って文字を描画
	draw_string(font, Vector2(32, 32), "Hello world.")
```

これでひとまず自由に文字を描画できます。

![test_string__DEBUG_.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/43772/1dace34e-057b-d521-1336-486a3b43b858.png)

# 日本語フォントの表示
ただ、デフォルトフォントは `BitmapFont` のため

* フォントサイズの変更ができない
* 日本語が文字セットに含まれていない (日本語が表示できない)

という問題があります。

なので日本語フォントを読み込んで描画する方法を紹介します。
フォントデータは M+ FONT を使うとします。

* [M+ FONT](https://mplus-fonts.osdn.jp)

M+ FONTの "mplus-1c-medium.otf" を読み込んで文字を描画するサンプルコードは以下のとおりです。

```gd
extends Node2D

var font = DynamicFont.new()

func _ready():
	# フォントデータの読み込み
	var font_data:DynamicFontData = preload("res://mplus-1c-medium.otf")
	
	# DynamicFontにフォントデータを設定
	font.font_data = font_data
	
	# フォントサイズを設定
	font.size = 24
	
	# アウトラインをつける
	font.outline_size = 2
	font.outline_color = Color.white
	
func _draw():
	# 文字を赤色で描画
	draw_string(font, Vector2(32, 32), "ハローワールド", Color.red)
```

`preload()` で読み込むと `DynamicFontData` となるので、それを `DynamicFont.font_data` に設定します。

日本語の文字を赤くして、白いアウトラインをつけて描画することができました。

![test_string__DEBUG_.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/43772/f1134fa3-3f21-5464-364c-6aa473d84c6b.png)


# 参考

* [GODOT DOCS » Godot API » DynamicFont](https://docs.godotengine.org/ja/stable/classes/class_dynamicfont.html#class-dynamicfont)
* [How to draw strings? - Godot Engine - Q&A](https://godotengine.org/qa/28760/how-to-draw-strings)
動画編集について

https://twitter.com/toripo_/status/1312677132716261377?s=20

Vrewで入力したテロップの高さを1発で揃える方法

1.任意のマスタースタイルを適用

2.エフェクトコントロールでお好みの高さを設定

3.ベクトルモーションをプリセット保存

4.テロップを一括選択して3で保存したプリセットを適用