OmniAICreator/Qiita-1.07M huggingface dataset:
IPAフォントのダウンロード方法と使い方

IPAフォントとは、一般社団法人「文字情報技術促進協議会」が公開している無料の日本語フォントです。

Windowsアプリを Visual Studio で開発する場合、ほぼ使う機会はありませんが、海外製のライブラリ（特にPythonのライブラリ）でたまに使う場合があります。

そこで、忘備録を兼ねて、IPAフォントに関する概要と、ダウンロード方法、使い方を記載しておきます。

## IPAフォントのラインアップ

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/887e51b7-35d4-dc7f-a9a2-de038f08777c.png)

2022年5月時点において、IPAには以下の６種類のフォントが用意されていました。

IPAexは最近登場したフォントであり、１つのフォントの中で和文は固定文字、欧文はプロポーショナルという、異なったフォント幅が使われているのが特徴です。

## ダウンロード方法

ダウンロード方法は公式サイトから行います。

### IPAexフォントのダウンロード

https://moji.or.jp/ipafont/ipaex00401

[公式サイト](https://moji.or.jp/ipafont/ipaex00401/)には、IPAex明朝とIPAexゴシックのフォントファイル（TTFファイル）の両方がまとめて入ったZIPファイルと、それぞれフォント毎のZIPファイルが用意されています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/18dd4ff0-5b8f-5a08-66f6-ac661722925b.png)


### IPAフォントのダウンロード場所

https://moji.or.jp/ipafont/ipa00303

[公式サイト](https://moji.or.jp/ipafont/ipa00303/)には、IPA明朝の固定幅とプロポーショナル、IPAゴシックの固定幅とプロポーショナルの４種類が１つにまとめられたZIPファイルと、それぞれのフォント毎のZIPファイルが用意されています。

この他に、TTCファイルというものもあります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/f773fcaf-0f7e-bc82-fe03-c384c15a494c.png)


TTCファイルは複数のTTFファイルを格納するためのフォーマットなので、こちらを使ってもOKです。

## ダウンロードしたZIPファイル解凍後のフォルダ構造

下記は、ダウンロードしたZIPファイルを解凍した際のフォルダ構造の例です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/ed12ab4e-944b-9974-2c6b-09a9a5db004b.png)

## インストール方法と使い方

WindowsアプリやVisual Studio等の開発環境でフォントを使いたい場合と、海外製のライブラリにフォントを直接指定する場合とで２通りのやり方があります。

### WindowsアプリやVisual Studio等の開発環境で使う場合

解凍したTTFファイルをダブルクリックすると、フォントのサンプルが表示されます。

ここで「インストール」をクリックすると、Windowsにフォントがインストールされます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/2c9fe2bd-8209-00ee-3c4e-0f692938aa06.png)

インストールが完了すると、ワードやエクセルのフォントから選択することが可能になります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/150844ec-c14e-2dd1-212a-af82e2a4aeb3.png)


## 海外製のライブラリにフォントを直接指定する場合

主にPythonのライブラリで、日本語フォントを指定する必要があるケースですが、ZIPファイルを任意のフォルダに解凍し、TTFファイルのフルパスをライブラリの引数に指定します。

```python
#ライブラリの引数にフォントパスを指定するサンプル
wordcloud = WordCloud(
    background_color=self.background_color,   # 背景色 
    font_path='D:/IPAexfont00401/ipaexm.ttf', # フォントのパス
    width=self.width,                         # 画像の横ピクセル数
    height=self.width,                        # 画像の縦ピクセル数
    min_font_size=self.min_font_size          # 最小のフォントサイズ
)
```

Windowsの場合、フォントは C:\Windows\Fonts というフォルダに全て格納されていますが、インストールしたフォントは別のフォルダに格納され、ここにはリンクのみ表示される仕様になっています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/34bc5833-bead-3393-36a5-82c3611e9137.png)


フォントを一旦インストールしてから、インストール先のPathをライブラリの引数に渡したい場合、フォントが実際に置かれているpathを指定しなければなりません。

Windowsの場合は下記に格納されていますので、ここを指定します。

```
　C:\Users\（ユーザ名）\AppData\Local\Microsoft\Windows\Fonts
```

## 各種IPAフォントのサンプルイメージ

参考として公開されているIPAフォントのフォントイメージを掲載しておきます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775985/c71a7f04-0f31-dae7-a636-d9177cca7fac.png)


## まとめ

ワードやエクセルなどのアプリケーションでIPAフォントを使うケースは稀ですが、プログラム開発や海外製ツールを利用する場合、時折IPAフォントのお世話になることが有ります。

今後、Windows標準のフォントが利用できず、何らかの日本語フォントが必要になった際は、この記事を思い出してください。
Nmap ポートスキャン


NMapを使用して、scanme.nmap.orgに対してポートスキャンを行います。
今回は以下のスキャン方法について学習した事を記述します。

-sS (TCP SYN スキャン)
-sT (TCP connect() スキャン)
-sU (UDP スキャン)


:::note info
[scanme.nmap.org](http://scanme.nmap.org/) について
ポートスキャンのテストを目的としたホストの事。以下、[リファレンス](https://nmap.org/man/ja/man-examples.html)抜粋
![hackme.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483720/6e172337-4259-3a4b-837d-992afc389793.png)


:::

## -sS (TCP SYN スキャン)
完全なTCPコネクションを確立する訳ではないので、
「ハーフオープンスキャン」と呼ばれる。
３WAYハンドシェイクのSYN(RST)/ACKまでを用いる。
ログに残らないのでステレス性が高い。
```
nmap -sS scanme.nmap.org
```
結果
![nmap -sS scanme.nmap.org.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483720/87831b14-2cb4-1cb7-c901-439ab9c39fe3.png)


## -sT (TCP connect() スキャン)
SYNスキャンを選択できない場合に指定するＴＣＰスキャン。（パケット送信権限を持たない場合）ＩＰｖ６ネットワークをスキャンする場合はこれを指定する。
ファイアウォールによってフィルタリングされている場合は、リクエストがドロップされるように設定されている。
Not shown: 〇〇 filtered ports　と表記される。ポートがフィルタリングされているという情報は攻撃者にとって有益な情報となるため、RSTを返却する事でセキュリティを向上させる対応とされている。
```
nmap -sT scanme.nmap.org
```
結果
![nmap -sT scanme.nmap.org.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483720/57a4aaf9-4f3b-f88a-81ac-eff36cba946c.png)



## -sU (UDP スキャン)
UDPスキャンは通常、ＴＣＰスキャンよりも処理に時間がかかる。しかしＵＤＰポートの一覧表を作成できるなどの利点もある。
DNS、SNMP、DHCP(それぞれ登録ポートは 53、161/162、67/68)はよく利用されるUDPサービスである
```
nmap -sU scanme.nmap.org
```
結果
![nmap -sU scanme.nmap.org.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483720/0c9fd201-68a9-a3c1-a6dc-6dd48b998e51.png)
Adobe Acrobat Reader を32bit版から64bit版にアップデートできないときの対処(Windows)

## 経緯
※とにかく対処法を知りたい方はこの章は飛ばしてよいです。

#### 普通にアップデートしてみる
社内用PCのマスター更新で64bit版へのアップデートの要望があり、
試験機にマスターイメージ戻し、
諸々のポリシーを外した上で
外部ネットワーク接続、
32bit版 Acrobat Reader のアプリケーション内から
普通にアップデートを実行。

→64bit版へのアップデートがかからない。

いろいろ情報収集するも、
「64bit版へのアップデートを*抑止する*方法」しか引っかからず。

#### 仕方がないので32bit版を一旦アンインストール
インターネット経由で Acrobat Reader のインストーラーを取得、
普通に起動して64bit版でのインストールを試みる。

（2024年5月現在、Adobe公式サイトからダウンロードできるAcrobat Reader のインストーラーは特別な指定をしない限り64bit版のオンラインインストーラーとなる）

順当にいけばこれで64bit版をインストールできるはず。
が。

「**インターネットの場所に接続出来ません。**」

いやいや・・・
今しがたインターネット経由でインストーラー落としてきたばっかりなんですけど？

こういうときは大抵、
アンインストール後に残ったレジストリのゴミが悪さをしているものである。

結局丸一日、レジストリを弄ってはインストール／アンインストールを繰り返して
見つけ出したのが以下の方法となります。


## 対処法
::: note 
32bit版 Acrobat Reader がインストールされている前提です。
インターネット環境への接続が必要です。
:::
::: note warn
レジストリの編集・削除は、操作を誤ると予期せぬ挙動を引き起こす恐れがあります。自己責任で実行してください。
:::

#### 1\. 原因のレジストリを削除する
キー名：HKLM\SOFTWARE\Adobe\Installer
エントリ名：MigratedTo64

キー名：HKLM\SOFTWARE\Adobe\Installer
エントリ名：UWP_APP_PACKAGE_FULLNAME

以下削除コマンド
```
reg delete "HKLM\SOFTWARE\Adobe\Installer" /v "MigratedTo64" /f
reg delete "HKLM\SOFTWARE\Adobe\Installer" /v "UWP_APP_PACKAGE_FULLNAME" /f
```

#### 2\. Acrobat Reader のアップデート実行
Acrobat Readerを起動し、
「メニュー → ヘルプ → アップデートの有無をチェック」をクリック

この時点では64ビット版へのアップデートは実行されません。
アップデートの有無に関係なく、Acrobat Reader を閉じます。

#### 3\. タスクマネージャーをチェック
タスクマネージャーを起動し、
「**Adobe Self Extractor**」がタスクに上がってくるのを待ちます。

![Reader64_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/946563/39981a44-ab4c-8c40-cc9e-73879be86d82.png)

こちらが上がってきたら、
32bit版のアンインストールと64bit版のインストールが
バックグラウンドで進行していますので、
プロセスから Adobe Self Extractor が消えるのを待ちます。

#### 4\. アップデート完了
デスクトップを確認すると、

![Reader64_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/946563/124d9033-a7a5-0d3d-d937-0ce667436b40.png)

**新たに**「Adobe Acrobat」のショートカットがデスクトップに生成されています。

起動すると、

![Reader64_3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/946563/f0e395da-83c8-04fc-fcf9-3ed2f09f145c.png)

上記のポップアップが表示され、
無事に64bit版へのアップデートが完了したことが分かります。


## なぜアップデートできなかったのか
#### ■任意で抑止する場合
そもそも、64bit版へのアップデートを*抑止する方法*は Adobe 公式が公開しています。

https://helpx.adobe.com/jp/acrobat/kb/about-acrobat-reader-dc-migration-to-64-bit.html

>Acrobat Reader 32 ビットアプリケーションが自動的に 64 ビットバージョンにアップグレードされないようにするには、アプリケーションを最初に起動する前に、次のレジストリキーを作成します。
>
>HKEY_LOCAL_MACHINE\SOFTWARE\Policies\Adobe\Acrobat Reader\DC\FeatureLockDown に移動します。
>
>以下のキーを作成します：
>キー：bUpdateToSingleApp
>データタイプ： REG_DWORD
>デフォルト値：0

しかし、ここに書かれているレジストリ値は試験機では確認できませんでした。

#### ■アップデートができなくなる条件
いちおう、以下の状況の再現性を取れたため記しておきます。

・32bit版をインストール
・前述の対処法を実施、64bit版に置き換える
　**→このタイミングで新たに「MigratedTo64」のエントリが生成される**
・64bit版をアンインストール
　**→ MigratedTo64 のエントリは残ったまま**
 ・32bit版をオフラインインストール（詳細略）
 ・MigratedTo64（とUWP_APP_PACKAGE_FULLNAME） がトリガーとなって
 　アップデートが抑止された状態になる
  

#### ■原因
・前任者がはじめに64bit版をインストール
・しかし当時の要件は32bit版だったため、
　64bit版をアンインストール → 32bit版で再インストール

  おそらく、こういうことだったんじゃないかなあと思います。


## まとめ
理屈としては納得できる挙動ではあるんですけどね。
64bit → 32bit とした後に、
また勝手に64bit版へのアップデートが走らないようにするのは合理的です。

でもなあ。
レジストリの操作を前提とするくらいだったら、
ここに挙げた仕様も公式に載っけておいてほしかったな～。

貴重な時間をこんなことで消費する僕みたいな人が
一人でもいなくなりますように。
以上。
Setting Up business in Mainland of United Arab Emirates

Setting Up business in Mainland of United Arab Emirates

The companies require legal sanctity before doing business in United Arab

Emirates. For conventional businesses in UAE, the Economic Department

is the authority which regulates all the procedures and requirements. These

are authorities for licensing to embark on economic activity in the Emirate.


1. Dubai Economic Department.

2. Sharjah Economic Department.

3. Abu Dhabi Economic Department.

4. Ras al Khaimah Economic Department.

5. Fujairah Economic Department.

6. Umm al Quwain Economic Department.

7. Ajman Economic Department.


Types of Licenses in conventional Business

Industrial license
 Commercial license
Craft license
Tourism license
 Agricultural license
Professional license

Important note: A business license may include more than one activity in one

business activity.


Legal Forms of Business

The first step to kick-start your business is to choose the economic activity and the second step is to decide on the legal form which caters for your business model. Here are the legal forms of companies which the Economic Department recognizes.

General Partnership.
 Limited Partnership.
Limited Liability Company.
One Person Limited Liability Company.
Sole proprietorship.
Civil company.
Public shareholding Company.
Private Joint-stock Company.
Representative Office.
Branch of Free Zone Company.
Branch of Foreign Company.
Branch of Local Company.
Branch of Company Based In another Emirate.
Branch of GCC Company.
Government Liaison office.
Foreign Ownership of Companies

foreigners/ ex-pats/non-GCC citizens are allowed to establish companies without local service agents with 100 per cent ownership of those companies, most of the commercial and

industrial activities are included in that list with the exception of some special activities. The foreigner can acquire the license for the above-said activities in the following two forms.


1. Limited Liability Company.

2. One-Person Limited Liability Company.


Special Impact  Activities


These are seven special activities in which a foreigner/foreign company

cannot hold 100 per cent ownership of the business in UAE. These activities

are called strategic impact activities.

1. Security, defence, and military-type activities.

2. Currency Printing.

3. Banks, exchange bureaus, finance institutions and insurance activities.

4. Telecommunications activities.

5. Hajj and Umrah Services.

6. Holy Quran Recitation Centers.

7. Services related to the fisheries sector.


Above said activities are special activities in which shareholdings of citizen

are determined by the concerned authorities along with shareholdings of

foreigners/foreign companies who wish to invest in these sectors albeit

in the fisheries sector, the citizen shall have 100 per cent ownership.
Website link>https://www.tncconsultants.ae/blog
【生成AIアプリ100チャレンジ】（21）格言検索

https://ai.nuevo.jp/aphorism/

![スクリーンショット 2024-05-07 20.18.35.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/398694/dc5b311a-c93c-3d90-6a26-5b35623445df.png)


開発環境

|  |  |
|:---:|:---:|
| Server | lightSail |
| Language | Python3.11 |
| Framework | Django |
| DB | sqlite3 |

ローカル環境ではPythonのvenvを使用。エディタはvs codeです。
目的
格言・名作を検索してくれるアプリ。
元気になりたいとか、やる気を出したい、仕事、人生で悩んでいるときに格言を見つけてくれる。

# コード
```python:qiita.rb

    try:
        OPENAI_API_KEY = os.environ['OPENAI_API_IMAGE_KEY']
    except KeyError:
        return HttpResponse("OPENAI_API_APIキーが設定されていません。", status=500)
    try:
        API_KEY = os.environ['DEEPL_API_KEY']
    except KeyError:
        return HttpResponse("DEEPL_APIキーが設定されていません。", status=500)
    translator = ""
    english_result = ""
    japanese_result = ""
    if request.method == "POST":
        form = ChatForm(request.POST)
        if form.is_valid():
            category = form.cleaned_data['category']
            details = form.cleaned_data['texts']
            try:
                def translate_text(text, auth_key, source_lang, target_lang):
                    translator = deepl.Translator(auth_key)
                    result = translator.translate_text(text, source_lang = source_lang, target_lang = target_lang)
                    return result.text
                details = translate_text(details, API_KEY, 'JA', 'EN-GB')
                client = OpenAI(
                    api_key = OPENAI_API_KEY,
                )
                response = client.chat.completions.create(
                    model="gpt-4",
                    messages=[
                        {
                            "role": "user",
                            "content": f"""
                            You are a historian.
                            What are some sayings of famous people from the past and present and what is the name of the famous person?
                            category is {category} And about {details}
                            Please pick three aphorisms.
                            Please output in the form of ' aphorisms <br /> by speaker '.
                            """
                        },
                    ],
                )
                english_result = response.choices[0].message.content
                japanese_result = translate_text(english_result, API_KEY, 'EN', 'JA')
            except Exception as e:
                return HttpResponse(f"API呼び出し中にエラーが発生しました: {str(e)}", status=500)
        else:
            return HttpResponse("フォームのデータが無効です。", status=400)
    else:
        form = ChatForm()

```

各フレームワークの課題に合わせて出力されます。

アプリ画面
![スクリーンショット 2024-05-07 20.18.35.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/398694/dc5b311a-c93c-3d90-6a26-5b35623445df.png)


感想
格言・名言を検索して、発言者とともに出力してくれます。
日本語と英語で出力されます。
[Vite] Docker内でnpm run devしてもアクセスできない時の対処法

## 実現したいこと
ホストマシンから、Docker内で動く開発サーバへアクセスしたい。

## TL;DR
以下のコマンドを実行すると、開発サーバをexposeできる。
```bash
npm run dev -- --host
```

## 環境
```
npm  == 10.7.0
vite == 5.2.11
```

## 試したこと
とりあえず通常通りサーバを起動してみる。
```bash
npm run dev
```
すると、
```bash
VITE v5.2.11  ready in 284 ms

  ➜  Local:   http://localhost:5173/
  ➜  Network: use --host to expose
  ➜  press h + enter to show help
```
このように表示された。このままでは、Dockerコンテナのローカルネットワークからでないと、開発サーバへアクセスできない。

そこで、言われたように`--host`を付して様子を見てみる。
```bash
npm run dev --host
```
すると、
```bash
VITE v5.2.11  ready in 288 ms

  ➜  Local:   http://localhost:5173/
  ➜  Network: use --host to expose
  ➜  press h + enter to show help
```
あれ? まだexposeできていないみたい。

## 原因と対処
どうやら、`dev`スクリプトのpositional argumentとして渡されるべき`--host`が、`npm`のオプションとして認識されてしまっているようです。
`npm`コマンドには`--host`というオプションが存在しないので、`npm run dev`と同じ結果が返ってきたと考えられます。

もう少し詳細に見てみましょう。
```json:package.json
"scripts": {
    "dev": "vite",
  }
```
まず、今呼び出そうとしている`dev`スクリプトの定義は上の通りです。そして、`vite`コマンドには、hostのIPアドレスを指定するための`--host`というpositional argumentが存在します。

```bash
npm run dev --host
```
一方でこのコマンドは、一見`--host`を`dev`スクリプトに渡しているようですが、実際には`npm`の(存在しない)オプションとして扱われています。そこで、
```bash
npm run dev -- --host
```
このように、`dev`の後ろに`--`を挿入して、以降の引数がオプションではなく、positional argumentであることを教えてやれば良いのです。
ご存知の方も多いように、`--`はUNIX標準の引数表現であり、それを利用すれば解決できます。

## 参考文献
https://stackoverflow.com/questions/71939532/npm-run-dev-host-network-not-exposed
https://zenn.dev/feb19/articles/bf403840fc57e8
https://megu-tech.hatenablog.com/entry/2019/10/09/121432
https://ja.vitejs.dev/config/server-options
https://suzu-mono-gram.com/blog/local-server-access-iphone/
【Go言語学習】チャネル( Channel )

# A Tour of Goでの説明

Channels
チャネル( Channel )型は、チャネルオペレータの <- を用いて値の送受信ができる通り道です。
https://go-tour-jp.appspot.com/concurrency/2

# ゴルーチン間で値のやり取り
ゴルーチンは非同期だけど、チャネルを使って同期させる。
情報処理検定で出てくる、キュー（先入れ先出し、FIFO）の動作。最初にチャネルに送信したデータが最初に受信される。スタック（後入れ先出し、LIFO）ではないイメージ。
mainゴルーチンの最後にチャネル受信を用意しておくと、全終了を待たせることができる。

# デットロック
チャネルへの送信操作は、そのデータが受信されるまでゴルーチンをブロックするため、同じゴルーチン内でチャネルの送受信を行うとデッドロックが発生する。→バッファ付きチャネルを使用すれば解消する。


# 試してみた
```go
package main

import (
	"fmt"
	"time"
)

func main() {
	ch1 := make(chan int)
	ch2 := make(chan int)

	go func() {
		time.Sleep(5 * time.Second) // 二秒
		ch1 <- 1
	}()

	go func() {
		time.Sleep(3 * time.Second) //一秒
		ch2 <- 2
	}()

	for i := 0; i < 2; i++ {
		select { //コードの記載順序に関係なく、先に到達した方が実行される
		case x := <-ch1:
			fmt.Println(x)
		case y := <-ch2:
			fmt.Println(y)
		}
	}
}

/* A Tour of Goのselect
package main

import "fmt"

func fibonacci(c, quit chan int) {
	x, y := 0, 1
	for { //3.無限ループ
		select {
		case c <- x: //4.ここで1に値が送られる、10回繰り返す
			x, y = y, x+y
		case <-quit:
			fmt.Println("quit")
			return
		}
	}
}

func main() {
	c := make(chan int)
	quit := make(chan int)
	go func() {
		for i := 0; i < 10; i++ {
			fmt.Println(<-c) //1.ここでいったん止まり、2が実行され、10回送られてきた後、forを抜ける
		}
		quit <- 0 //5.2の呼び出しを終了させる
	}()
	fibonacci(c, quit) //2.呼び出す
}

*/
```
https://github.com/kabasunny/GoPractice/blob/main/Channels/Channels.go
【CSS】position: fixed の使い方

## 基本的な使い方
ある要素を画面に固定配置する際に使用される。

<固定ヘッダーの例>
```html
<header>
  <div class="container">
  <p>これはヘッダーです。</p>
  </div>
</header>
```

```css
.header {
/*ヘッダーを上部に固定*/
  position: fixed
  top: 0;
}
```


## z-indexについて
position: fixedと併用して使用する。
要素同士の重なり順を指定する。


```css
.header {
/*ヘッダーを上部に固定*/
  position: fixed
  top: 0;
  /*数字が大きいほうが上のレイヤーになる*/
  z-index: 10;
}

```
AWS Linux OS で mariadb-connector-c を mysql-client に置き換えます

# 理由

mariadb-connector-c クライアントがアプリケーション (FastAPI に基づいて構築された) のパフォーマンスの問題を引き起こしている可能性があると考えられます。

```sh
yum remove -y mariadb-connector-c
yum install -y https://dev.mysql.com/get/mysql80-community-release-el9-1.noarch.rpm
rpm --import https://repo.mysql.com/RPM-GPG-KEY-mysql-2023
yum install -y mysql-devel
```
Flutter 〜コンストラクタのsuper.key〜

いろんな説明を読んでもいまいちピンとこないFlutterの
「コンストラクタ({super.key});」の部分について調べてみた。


```dart
class Xxx extends StatelessWidget {
    Xxx({super.key}); //ここな

    @override 
    Widget build(BuildContext context) {
        return Container();
    }
}
```

「super」というキーワード自体は、親クラスのコンストラクタやメソッドを呼び出すために使用されるが、「super.key」の文脈での使用は、親クラスのコンストラクタに引数を渡す特定の目的に限定される。
　
super.keyはスーパークラス（StatelessWidget）のコンストラクタにキーを渡しており、これによりウィジェットが適切に初期化される。
　
順番としては、
①別のクラスからXxxクラスのウィジェットを生成
②Xxxクラスでは渡されたパラメータをsuper.keyという書き方でスーパークラスに渡す
③スーパークラス（StatelessWidget）は、この渡されたキーを受け取り、ウィジェットの識別子として内部的に保持する。

**Javaの感覚で「super.keyはスーパークラスで保持しているkeyという値を参照」と考えてしまいそうだが、これが大きな誤解を招く。**

Javaのサンプル
```java
public class MathUtility {
    public static final double PI = 3.14159;

    public static int add(int a, int b) {
        return a + b;
    }
}

// どこか他のクラスから
double piValue = MathUtility.PI;
int result = MathUtility.add(5, 3);

```
この例では、MathUtilityクラスに静的な変数PIと静的なメソッドaddが定義されています。外部のクラスからこれらの静的メンバーには、クラス名を使って直接アクセスする。
　

Flutterでウィジェットを作成する際、ほとんどのウィジェットコンストラクタにはkeyという名前付きパラメータが用意されている。
これにより、開発者はウィジェットに任意のキーを指定して、そのウィジェットの一意性や状態の管理を容易にすることが可能となる。
　

Dartにおいても、同様の概念が存在する。
クラスの静的メンバーは、インスタンス化せずにクラス名を通じてアクセスすることができる。

```dart
class Constants {
  static const double pi = 3.14159;
}

// アクセスする
double myPi = Constants.pi;

```

Flutterにおいて、ウィジェットのコンストラクタにkeyパラメータを渡す場合、このキーはインスタンスのプロパティとして扱われ、ウィジェット固有の識別に使用される。

これは静的アクセスとは異なり、特定のウィジェットのインスタンスに属するものになる。

```dart
var myWidget = Xxx(key: Key('unique_key'));
```

super.keyはスーパークラスのkey値をコンストラクタに渡す、というように見えるけど、keyというパラメーターに値がkey: xxxのような形式で渡された場合はスーパークラスのコンストラクタにkeyで指定された値を渡す、という意味になる。
　

 super.keyという記載方法ができるようになったのはDart 2.12のリリースから。
 それ以前では下記のような記載だった。
 ```dart
 class Xxx extends StatelessWidget {
  Xxx({Key? key}) : super(key: key);  // key をスーパークラスのコンストラクタに渡す
  @override
  Widget build(BuildContext context) {
    return Container();
  }
}
```

Dart 2.12から「Xxx({super.key});」となり、書きやすくなった。
「Xxx({Key? key}) : super(key: key);」の記法は現在でも有効だが、Dart 2.12以降ではsuper.keyのようにパラメータの転送をより簡潔に行えるようになったため、コードをシンプルに保つことができる。
【Next.js】Storybookで画像が表示されない時

# はじめに

こんにちは、エンジニアのkeitaMaxです。

# 困っていたこと

`npm run dev`で立ち上げた時は画像が表示されるのに、`npm run storybook`でStorybookを立ち上げて確認すると画像が見えなくて困りました。

# 結論

```
"staticDirs": ["../public"],
```

この記述を`.storybook/main.ts`に入れると画像が表示されました。

Styorybookで画像を読み込ませるように設定してあげないとダメなようです。


# おわりに

Storybookの設定が色々漏れているので、一度しっかりStorybookのリファレンス読もうかなと思います。

この記事での質問や、間違っている、もっといい方法があるといったご意見などありましたらご指摘していただけると幸いです。

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

# 参考

https://qiita.com/RYA234/items/0b040132532ea71580f4
Bootstrap上書き

## .comtainer
```css
/* 親要素のbootstrapのconteinerクラスを上書き */
.container{
    /* 左右の余白をなくす */
    width: 100% !important;
    max-width: 100% !important;
    min-width: 100% !important;
    margin-left: 0px !important;
    margin-right: 0px !important;
}

```
【bin/】rails の違いについて

## rails server と bin/rails serverの違いについて

rails server と bin/rails serverの違いが気になり調べたので以下まとめておきます。

**【結論】**
**「rails server」の方は システム全体でインストールされている rails を使用し,**
**「bin/rails server」の方は アプリケーション固有の Bundler 環境に基づいて実行されます。**

「rails server」の方の**システム全体でインストールされているrailsに対して、コマンドを実行する**とは

例えば、
同じPC内で複数のrailsアプリを作成していた場合、
それぞれのアプリでインストールしているgemが異るとして、rails serverでrailsを立ち上げると、システム全体に対してアクションを起こすため、グローバルにインストールされた gem の影響を受けやすく、そのアプリケーションで期待されるGemfileにならない可能性があります。

一方、
「bin/rails server」では、
アプリケーション固有の Bundler 環境（Gemfileで定義された依存関係）で実行されます。そのため、異なるプロジェクトやグローバル環境の gem の影響を受けにくく、プロジェクトで期待されるバージョンや設定でコマンドが実行されます。

railsの起動に失敗した場合、gemの依存関係がエラー原因であることも考えられるため、
bin/rails serverで再度起動してみるのもよいかと思いました。

【補足】
Windowsでは、「bin/rails server」で実行しても反応がなかったので、
「bundle exec rails server」で実行しました。
bundle exec を使用すると、Bundler で管理されているプロジェクト固有の gem 環境でサーバーを起動できます。
HAProxyとKeepalivedの設定ファイルをchezmoiでgit管理する

まず、chezmoiというのはドットファイルを管理するソフトです。よって`/etc`下にあるコンフィグファイルの管理には本来適していません。やめておいたほうが良いです。

ただ、ほとんど一緒だけどほんの少しだけ違うkeepalivedのコンフィグファイルをgit管理するにあたり、chezmoiを使用するのが一番簡単だったので、使用することにしました。

## haproxy.cfgをchezmoiで管理する
これはどの端末も一緒になると思うので簡単です。
`/etc/haproxy/haproxy.cfg`を`~`にコピーします。

```sh
cp /etc/haproxy/haproxy.cfg ~/
```

そして元のファイルの名前を変えておきます。

```sh
mv /etc/haproxy/haproxy.cfg.bak
```

chezmoiに追加

```sh
chezmoi add ~/haproxy.cfg
```

最後にシンボリックリンクを貼る

```sh
ln -s /root/haproxy.cfg /etc/haproxy/haproxy.cfg
```

当然ながらrootUserでない場合は`/home/user`にしておいてください。今回はhaproxyとkeepalivedしか入っていないlxcコンテナなのでrootです。

## Keepalivedを環境に応じてちょこっと変える

```sh
chezmoi cd
```

そこで`keepalived.conf.tmpl`ファイルを作成。

```conf:keepalived.conf.tmpl
vrrp_script chk_haproxy {
    script 'killall -0 haproxy' # faster than pidof
    interval 2
}

vrrp_instance haproxy-vip {
   interface eth0
    state {{ if eq .chezmoi.hostname "master" }}MASTER{{ else }}BACKUP{{ end }}
    priority {{ if eq .chezmoi.hostname "master" }}200{{ else }}100{{ end }}

    virtual_router_id 51

    virtual_ipaddress {
        0.0.0.0/26
    }

    track_script {
        chk_haproxy
    }
}
```

設定は適当ですが、`.chezmoi.hostname`でhostnameによってMASTER, BACKUPを切り替えができます。priorityについても同様。あとは次にchezmoi applyとしたときに~/keepalived.confがhostnameに応じて自動的に生成されます。あとvirtual_ipaddressは自分の設定したいVIPを入れておいてください。念のため。

```sh
chezmoi apply
ln -s /root/keepalived.conf /etc/keepalived/keepalived.conf
```

これでkeepalived, haproxyの設定ファイルをchezmoiで管理できました。一応、etckeeperなどもありますが、この要件を満たすのにはちょっとやりすぎ感があるので、シンプルに使えるchezmoiでもどうでしょう。まあ本来はconfigファイルを管理するソフトじゃない、ということをちゃんと意識した上で使ったほうが良いと思います。
ChatGPT が Teams で 記事を要約してくれる BOT を作ってみた

## はじめに

作ったものは記事のタイトル通り、Microsoft Teams に記事の URL を貼ったら、その内容を要約して投稿してくれる仕組みです。

Teams で情報共有している現場は多くあると思いますが、共有してもらった記事を全部読むのは意外に大変です。そんなとき短文で要約して、サッと中身がどんな内容なのか分かると便利だなと思い作ってみました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/409268/e958a77a-1886-d035-b9c7-cd2e6a0d8219.png)


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/409268/f266c86d-82c4-043f-e475-74b96994e233.png)

英語の記事もそこそこいい感じに日本語で要約してくれます。↓↓

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/409268/93c7311f-fb5f-551f-67f8-909739ecb025.png)


## 処理の流れ
Azure の Logic Apps でフローを組んでいます。
※PowerAutomate でも実装可能ですが、今回は HTTP コネクタを無料で使いたいので、Azure Logic Apps を使います。

Teams のコネクタをトリガーにし、Azure Functions と Azure OpenAI API を入れて、最後に要約結果を Teams に投げています。

**①Teams に新たな投稿があるかチェック（5 分おき）** 
↓
**②Azure Functions で投稿された URL 内のテキストをスクレイピング**
下の「HTTP - Get Content 」の部分です。
（Python の BeautifulSoup で実装しています）
↓
**③要約結果を Azure OpenAI の API に投げて、GPT-4 なりで要約**
下の「HTTP - Summarize」の部分です。
↓
**④要約結果を Teams コネクタでチャットに投げる** :tada:

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/409268/33681855-1879-0e34-47d3-5d40f5ab6bd7.png)


## 実際のコード
上記 ② で使用している Azure Functions のコードのみ紹介します。


``` python
import azure.functions as func
import requests
import json
from bs4 import BeautifulSoup
from extractcontent3 import ExtractContent

app = func.FunctionApp(http_auth_level=func.AuthLevel.FUNCTION)

@app.route(route="TextExtraction")
def TextExtraction(req: func.HttpRequest) -> func.HttpResponse:

    # Teams に投稿された情報を取得
    tag = req.get_json().get('tag')
    req_soup = BeautifulSoup(tag, 'html.parser')
    link = req_soup.find('a', href=True)
    url = link['href']

    # URL からウェブページを取得
    response = requests.get(url)
    response.raise_for_status()  # エラーならここで例外を発生させる

    # URLからタイトルと中身のテキストを抽出する
    html = response.text
    extractor = ExtractContent()
    opt = {"threshold": 0}
    extractor.set_option(opt)
    extractor.analyse(html)
    text, _ = extractor.as_text()
    soup = BeautifulSoup(html, "html.parser")
    title = soup.find("title").text

    # 記事のタイトルと中身のテキストを返す
    result = json.dumps({"title": f"{title}", "content": f"{text}"})
    return func.HttpResponse(result, mimetype="application/json")

```
Azure OpenAI の API の利用方法などはドキュメントなどに詳しく書かれているので今回は省略します。以下に参考リンクを置いておきます。

https://learn.microsoft.com/ja-jp/azure/ai-services/openai/reference#chat-completions
## さいごに
おそらく以下のケースには対応できないので、対応するためには改良が必要と思います。
- 貼られた記事が複数ページで構成されている（ページングで構成されている）場合、すべてのページを参照した要約できない（１ページ目だけをもとに要約する）
- 複数の URL を Teams に投稿した場合
Docker上のMySQLをphpMyAdminで簡単にGUI操作

- Docker v24
## はじめに
Dockerで作成したデータベースの中身を確認、操作する際に、毎回MySQLのコンテナに入ってコマンドを叩いていたのですがとても面倒でした。

`phpMyAdmin`のコンテナを作ると簡単にGUI操作ができて便利でしたので紹介します。

## phpMyAdminのコンテナを追加

`compose.yaml`にphpMyAdminのコンテナ定義を追記します

``` yaml
services:
  mysql:
    image: mysql:8.0
    environment:
      MYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PASSWORD}
      MYSQL_DATABASE: ${MYSQL_DATABASE}
    ports:
      - 3306:3306
    volumes:
      - mysql-data:/var/lib/mysql

# phpMyAdminコンテナを追記
  phpmyadmin:
    image: phpmyadmin
    depends_on: # 依存関係
      - mysql
    environment:
      - PMA_ARBITRARY=1 # 任意のホストを設定
      - PMA_HOSTS=mysql # ホスト名
      - PMA_USER=root # ユーザー名
      - PMA_PASSWORD=${MYSQL_ROOT_PASSWORD} # パスワード
    ports:
      - "3001:80"
    volumes:
      - pma-sessions:/sessions

volumes:
  mysql-data:
  pma-sessions:
```

コンテナ起動後`http://localhost:3001/index.php`にアクセスすると表示されます。
個人開発で一部DBとして使用しているContentfulをSupabaseに移行した

## はじめに
個人開発で運営しているWebサービスの一部DBとして使用しているContentfulをSupabaseに移行した話をまとめました。

## 個人開発のWebサービスをContentfulからSupabaseに移行した経緯
### 無料枠を超えそう

Contentfulの無料枠で使用しているのですが、無料枠だとレコード数が1万件となっており、徐々に上限に近づいていました。このままだと半年後くらいに上限にいきそうだったので、移行することにしました。

ちなみに有料プランも考えたのですが、1ヶ月300ドルと高いのとレコード数の上限が5万件といずれまた上限に達する時がきてしまうと思ったのでやめました。

### ContentfulのAPI経由での取得なので検索性がちょっと悪い

Contentfulからのデータを取得する際にAPI経由で取得するのですが、Contentfulが指定した条件で取得するため、若干使いづらいところがありました。

具体的に全文検索でmatchを使うのですが、データによってはヒットするはずなのに引っかからなかったりしていました。今後、Webサービスの検索性を高めるためにも移行しておきたかったです。

### Webサービスの変化

今後WebサービスとしてCGM要素が追加されることもあり、ContentfulのAPIにGETだけでなくPOSTやUPDATEのリクエストを頻繁に行われることになります。

初期の頃の静的なコンテンツメインの情報サイトからCGMサービスとして変化していく中で、今後もContentfulを使っていくことに違和感を感じ、ちゃんと自前でDBを用意してあげる方が今後の保守性や拡張性においても良いのではないかと思いました。

## Supabaseにした理由

Contentfulを使っていたことからサーバレスのアプリケーション構造になっており、その構造でも導入できるSupabaseを選択しました。

またSupabaseにした理由として、RDBが使いたかったのとライブラリが用意され触った感じ使いやすかったためです。SupabaseのDBはPostgreSQLを使用しており、ライブラリのドキュメントも充実していました。

## ContentfulからSupabaseに移行するまでにしたこと
### Supabaseで開発環境と本番環境を用意

まずSupabaseで開発環境と本番環境を構築しました。アカウント登録してプロジェクト作成しました。

https://supabase.com/

### Supabase用のディレクトリを用意

次にWebアプリケーション内のソースコードを新しくSupabaseの接続用に作成しました。

Supabase用のDriverを用意して、ローカル環境で向き先をSupabaseにして実装をしました。

### ContentfulからSupabaseへデータ移行

ContentfulにあるデータをSupabaseのDBに移行しました。ContentfulからデータをGETしてSupabaseのDBにINSERTするスクリプトを書いて、そのスクリプトを実行することでデータ移行しました。

### 検証環境で確認

ローカル環境での開発が終わったら、実際に検証環境にあげて本番環境と同じ動作になるかを検証しました。

### 本番環境の向き先をSupabaseへ移行

検証環境の動作確認を終えて、問題ないことを確認した後、本番環境への移行作業を行いました。


## おわりに
やはり人力の動作確認やUTだとどうしても抜け漏れがあり、本番移行後に気づいたバグがいくつかありました。今後バグを発生させないようにするためにもE2Eの導入などが必要になりそうです。

とんとん拍子でいけると思ったら、実際に修正するコードが多かったり、データ移行にハマったりと思ったよりも時間がかかりました。

事前に調査してたとはいえ、移行作業はどうしても読めないことが多く、時間がかかってしまうなと改めて感じました。

## JISOUのメンバー募集中
プログラミングコーチングJISOUではメンバーを募集しています。
日本一のアウトプットコミュニティでキャリアアップしませんか？

気になる方はぜひHPからお願いします👇

https://projisou.jp/
JavaScript: 配列の雛型作成で高速化

配列を任意の値で初期化するには雛型から複製した方が高速です。しかし**複製自体を省略する事も可能**。objectを作る段階で既に初期化が完了しているという裏技を紹介します。[この記事でもちら～っとこっそり](https://qiita.com/mashuel/items/3358e8a075369b5f4255)触れている内容ですが、今回の記事はもう少し深掘りしていきます。
方法は極めて単純で、関数の`prototype`を配列化するだけです。
## benchmark
要素が数値限定の速度検証
```js
{// TypedArray雛型の複製。遅い
	let a=256, Narray=new Uint8Array(a), t=new Date;
	for(;Narray[--a]=a;);//雛型の初期化
	for(;a++<256;){
		let A=[];
		for(let i=0;i<1e4;)A[i++]=Narray.slice();
	}
	console.log(new Date-t);
}
{// 配列もどき。高速
	let a=256, Narray=function(){}, p=Narray.prototype=Array(a), t=new Date;
	for(;p[--a]=a;);//雛型の初期化
	for(;a++<256;){
		let A=[];
		for(let i=0;i<1e4;)A[i++]=new Narray;
	}
	console.log(new Date-t);
}
{// TypedArrayもどき。高速
	let a=256, Narray=function(){}, p=Narray.prototype=new Uint8Array(a), t=new Date;
	for(;p[--a]=a;);//雛型の初期化
	for(;a++<256;){
		let A=[];
		for(let i=0;i<1e4;)A[i++]=new Narray;
	}
	console.log(new Date-t);
}
{// TypedArray+配列もどき。超低速
	let a=256, Narray=function(){}, p=Narray.prototype=Array(a), t=new Date;
	for(;p[--a]=a;);//雛型の初期化
	for(;a++<256;){
		let A=[];
		for(let i=0;i<100;)A[i++]=new Uint8Array(new Narray);//遅過ぎるので少なめ
	}
	console.log(new Date-t);
}
```
ちなみに**昔は`prototype`自体にTypedArrayを指定すると、Error祭りが開催されまくっていた**ような気がするんですが、今回久々に検証してみたら動作しちゃいました。
不思議な事に**TypedArrayもどきはTypedArrayのmethodを全く使えません。lengthすら読めません**。

:::note info
初期化の計算量より配列作成後の要素参照や書き換えの計算量が高つく場合は、素直にTypedArrayの雛型を複製した方が有益です
:::

こんな変態行為が役立つ場面と言えば、同じ構造の木を大量生産する時等でしょう(splay木、huffman木等)。
## 文字列の配列
任意文字列の量産も高速化可能。
```js
function StrArray(){}; // 配列もどき
StrArray.prototype=[
	"土器土器デコ割れそう",
	"ドキドキで壊れそう",
	"testset",
	"read red paper"
];
// 文字配列もどき
let A=[];
for(let a=9;a--;)A[a]=new StrArray; //量産
console.log(A[0][0].slice());
console.log(A[0][1].slice())
```
## object型の配列
`prototype`のpropertyにobject型の何かを放り込むと意図しない動作となります。
```js
let Oarray=function(){}, p=Oarray.prototype;
p[0]=[0,11,222,3333];
p[1]={a:"AB", bc:987, def:["CD", 1.4142]}
p[2]=a=>a*a;

let A=new Oarray, B=new Oarray;
A[0][0]=893;
A[1].a="DEF";
console.log(A[0][0], B[0][0], A[1].a, B[1].a)
```
お分かりになったでしょうか? 異なる変数同士であたかも要素を共有しているかのように振る舞ってしまいます(当たり前)。こんな馬鹿げた事をするくらいなら、馬鹿正直に`class`でも使えという話です。ちなみに`class`の配列化は面倒です。
```js
class c{
[0]=1;
[1]="a";
[2]=[6,28,299792458]
}
let a=new c;
console.log(a[0],"\n",a[1],"\n",a[2])
```
などといった具合です。ただし上記のような方法はinstance生成が遅い上に、memory消費も多いという欠点があります。まさに本末転倒。
## classの注意点
前述の関数と同じように数値配列の雛型を作ってみます。
```js
class c{}
let a=256, p=c.prototype=[];
for(;p[--a]=a;); //要素を格納しているつもり
let b=new c;// instance生成
for(;a<256;)console.log(b[a++]," ")//undefined
```
おや? 何やら様子がおかしいですね。要素が`undefined`になっちゃってます。実は`c.prototype=[]`というのがまずいのです。正しくは以下のようにします。
```js
class c{}
let a=256, p=c.prototype; // 配列を設定しない
for(;p[--a]=a;); //要素を格納
let b=new c;// instance生成
for(;a<256;)console.log(b[a++]," ")//0...255
```
datacalsses-json: `to_dict()`でEnumのvalueを出力するには`encode_json=True`を指定する

# 環境
* Python 3.12.1
* dataclasses-json 0.6.5


# クラスの定義

```python
from enum import Enum
from dataclasses import dataclass
from dataclasses_json import dataclass_json


class Color(Enum):
    RED = 1
    GREEN = 2
    BLUE = 3


@dataclass_json
@dataclass
class Car:
    name: str
    color: Color

```

# 内容

`to_dict()`を引数なしで実行すると、`color`はEnumのインスタンスになります。`encode_json=True`を指定すれば、`color`はEnumのvalueになります。

```
In [39]: c2 = Car("name", Color.GREEN)

In [40]: c2
Out[40]: Car(name='name', color=<Color.GREEN: 2>)

In [37]: c2.to_dict()
Out[37]: {'name': 'bar', 'color': <Color.GREEN: 2>}

In [38]: c2.to_dict(encode_json=True)
Out[38]: {'name': 'bar', 'color': 2}
```


dataclasses-jsonのドキュメントには`encode_json`についての説明がなかったので、簡単ではありますが記事を作成しました。


# 補足


### `from_dict()`の挙動
`color`にはEnumのvalueまたはEnumインスタンスを指定することができました。


```
# Enumのvalueが含まれている
In [32]: c2 = Car.from_dict({"name":"bar", "color":2})

In [33]: c2
Out[33]: Car(name='bar', color=<Color.GREEN: 2>)

# Enumインスタンスが含まれている
In [34]: c3 = Car.from_dict({"name":"bar", "color":Color.BLUE})

In [35]: c3
Out[35]: Car(name='bar', color=<Color.BLUE: 3>)
```
Raspberry Pi + CODESYS + EtherCAT = CNCプロジェクトを公開 (OSS/GPL)

同時6軸のCNCです。
GitHubで公開して開発を進めます。

https://github.com/k-s-saki/RPi_CODESYS

FANUC用にCAD/CAMで生成されたGコードプログラムを、簡単な文字変換だけで動くようにしていますが、DINのGコードに足りない部分（主軸の回転数制御、工具補正、ワーク座標テーブル、その他）はCODESYSのプログラムや、UIでそれらしい機能を実装していくことになります。

CODESYSのプログラムについて、気が付いた点があれば、お知らせください。

ホビーや制御系の展示会のデモなどに使っていただけたら幸いです。


現在、GPLv3オープンソースプロジェクトとして公開しています。
KVMでシリアルコンソール接続


https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/9/html/configuring_and_managing_virtualization/proc_opening-a-virtual-machine-serial-console_assembly_connecting-to-virtual-machines#doc-wrapper

https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/8/html/configuring_and_managing_virtualization/assembly_connecting-to-virtual-machines_virt-getting-started#proc_opening-a-virtual-machine-serial-console_assembly_connecting-to-virtual-machines

https://access.redhat.com/ja/articles/227573
【Python】標準入力を受け取る方法（単数,複数）

# **はじめに**

個人的なメモ、調べたことをアウトプットしています。

間違いあればご指摘の程いただけますと幸いです。


# 単数の標準入力

### 文字列
`input()` にて標準入力を受け取る。

```python
input_line = input()
print(input_line)

#-----result--------
>>> apple
# apple
```

### 整数

 `int()` で`input()` の標準入力を整数型にフォーマットし取得。

```python
input_line = int(input())
print(input_line)

#-----result--------
>>> 24
# 24
```

# 複数の標準入力

### 文字列

`input()` の標準入力を`split()`　で半角スペースの位置で区切って取得。

```python
a,b = input().split()
print(a,b)

#-----result--------
>>> リンゴ ゴリラ
# リンゴ ゴリラ
```

カンマ区切りを取得するには`split(",")`で取得。

```python
a,b = input().split()
print(a,b)

#-----result--------
>>> リンゴ,ゴリラ
# リンゴ ゴリラ
```

### 整数

#### map 

`input()` の標準入力を`split()`で半角スペースの位置で区切って取得。

`map()`で各要素のマッピングを行う。

```python
n, x, y = map(int, input().split())
print(n,x,y)

#-----result--------
>>> 5 4 2
# 5 4 2
```

#### for 

`input()` の標準入力を`split()`　で半角スペースの位置で区切って取得。

`int(x) for in` でループして整数型にフォーマット。

```python
a,b=(int(x) for x in input().split())(
print(a)
print(b)

#-----result--------
>>> 8 9
# 8
# 9
```

# *まとめ*
入力パターンや取得方法は、まだまだパターンがあると思います。
まとめ次第、記事を書くかこの記事に追記していこうかと。
【Atcoder】ABC 128 C問題

# コンテスト名

AtCoder Beginner Contest 128

https://atcoder.jp/contests/abc128

# 考えたこと

。。。なーんもわからない

# 調べてみよう
**bit全探索**を使うらしい。*1

スイッチがon,offの2通りだから$2^N$の計算が必要
でもどうやったら**bit全探索**だと判断できるんだ？

>競技プログラミング（AtCoder）において、問題の制約が$N\leq10$とかの極端に小さい場合はbit全探索で解けないかを疑ったほうがいい。
その根拠は、$2^N$は$N=30$くらいで結構大きな数になる点である。





```python
n,m=map(int,input().split())
S=[]

for i in range(m):
    s=list(map(int,input().split()))
    s.pop(0)
    S.append(s)
    
p=list(map(int,input().split()))
count=0
for a in range(2**n):
    bool=True
    for b in range(m):
        sum=0
        for c in S[b]:
            if a>>c-1 & 1:
                sum+=1
        if sum%2!=p[b]:
            bool=False
    if bool==True:
        count+=1
print(count)
```
(@tttol 様のサイト*2を参考にさせていただきました。)

# bit全探索ってなんだ？
![スクリーンショット 2024-05-07 17.25.53.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3775488/78861d31-7a1e-2b27-2000-5cc6f8ee138a.png)
スイッチ1がon、スイッチ2がoff、スイッチ3がonだったら[1,0,1]すなわち101のように
2進数として表せる。

全てのスイッチの状態は$2^N$通りあるのでそれらを全探索する。

その際、例えば101においてスイッチ3がONであるかOFFかを調べるとき**ビット操作** *3を使う。
```python
 a>>c-1
 # -1する理由は0indexだから
```

# 参考

*1

https://drken1215.hatenablog.com/entry/2019/06/15/135300

*2

https://qiita.com/tttol/items/a519c8c4dd38df15d530

*3

https://note.nkmk.me/python-bit-operation/
# おまけ

bit全探索について鉄則にも少し書いてあった

https://book.mynavi.jp/ec/products/detail/id=131288
Arduino UNOで「1234567890ABCDEF」を「0,1,2,3,..,12,13,14,15」に変換して遊ぶ。



目的
bitmapをいろいろ操作するため



結果

![o_coq084.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/e6d6e170-7472-0032-07e1-e24c9e6d6024.jpeg)


プログラム

```c++


//ch_012__EF_to_0_1_2__14_15_UNO_1


#define hex_cov(aa)   ((aa<':')?aa-'0':aa-'A'+10)


// the setup routine runs once when you press reset:
void setup() {
  // initialize serial communication at 9600 bits per second:
  Serial.begin(9600);

  Serial.println();
  Serial.println("START");
  Serial.println();

  Serial.println((int)hex_cov('0'));
  Serial.println((int)hex_cov('1'));
  Serial.println((int)hex_cov('2'));
  Serial.println((int)hex_cov('3'));

  Serial.println((int)hex_cov('4'));
  Serial.println((int)hex_cov('5'));
  Serial.println((int)hex_cov('6'));
  Serial.println((int)hex_cov('7'));

  Serial.println((int)hex_cov('8'));
  Serial.println((int)hex_cov('9'));
  Serial.println((int)hex_cov('A'));
  Serial.println((int)hex_cov('B'));

  Serial.println((int)hex_cov('C'));
  Serial.println((int)hex_cov('D'));
  Serial.println((int)hex_cov('E'));
  Serial.println((int)hex_cov('F'));

} //setup


// the loop routine runs over and over again forever:
void loop() {
  delay(1);
} //loop



```





おまけ
----------------------------------------

オンラインコンパイラ

```c++


#include <stdio.h>
int main(void){
    // Your code here!
    
    printf("\nSTART\n");
    
#define hex_cov(aa)   ((aa<':')?aa-'0':aa-'A'+10)
    
    printf("%d\n",(int)hex_cov('0'));
    printf("%d\n",(int)hex_cov('1'));
    printf("%d\n",(int)hex_cov('2'));
    printf("%d\n",(int)hex_cov('3'));

    printf("%d\n",(int)hex_cov('4'));
    printf("%d\n",(int)hex_cov('5'));
    printf("%d\n",(int)hex_cov('6'));
    printf("%d\n",(int)hex_cov('7'));

    printf("%d\n",(int)hex_cov('8'));
    printf("%d\n",(int)hex_cov('9'));
    printf("%d\n",(int)hex_cov('A'));
    printf("%d\n",(int)hex_cov('B'));

    printf("%d\n",(int)hex_cov('C'));
    printf("%d\n",(int)hex_cov('D'));
    printf("%d\n",(int)hex_cov('E'));
    printf("%d\n",(int)hex_cov('F'));


}

```

```



START
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15


```
Amplify Gen2のデプロイ環境で急にTypeErrorになった

## 問題
もともとAmplifyのGen1でホスティングしていたReactのサイトがあるのですが、Gen2に移行したタイミングからかブラウザが真っ白になっていました。

developer toolのconsoleを見てみると`TypeError: Cannot read properties of null (reading 'useContext')`の文字が…！

ローカルでビルドしたアプリを起動してみたら問題なくブラウザ表示できるのでますます謎に。。

## 解決方法
moduleの依存関係に問題があるのかと思い、node_modulesとlockファイルを削除して再度ローカルでインストールしたらlockファイルに差分が出てきたので、そのままリポジトリにpushしてホスティングされたサイトを見たら問題なくサイトが表示されました！

私の場合はpnpmを使っているので、pnpm-lock.yamlを削除しました。

## 最後に
ホスティング先ではローカルと同じDocker Imageを使ってるので、環境差異はないと思ってたんですが、そうでもないのか…？と少しモヤモヤしますが、とりあえず解決できて一安心です。
【Googleスプレッドシート】QUERY関数で指定した番目の行だけを抽出する

### 備忘録としての短記事です。
先日QUERY関数で呼び出したデータを使用していて
「**3行目だけ欲しいな…**」ということがありました。

「**条件に一致した行**」を呼びたいというわけではなく「**指定した番目の行**」が呼びたいという状況です。前者ならQUERY関数のWhere句の使用等で解決ですが、後者の方法を案内した記事は見つけることが出来ませんでした。

なので、
やや無理矢理かもしれませんが以下のように書いて対応してみました。
```Ruby:完成した関数１
=QUERY(配列,"Limit 1 Offset 数値-1",0)
```
上記の「**数値**」の箇所に「**3**」と入力すれば、配列の3行目だけを呼び出せました。

:::note info
**Limit**
これは呼び出す行数の上限を指定する句です。
1を入れることで1行だけ呼び出せます。

**Offset**
データの上(1行目)から呼び出さない行数を指定する句です。
2を入れると上2行を無視するので3行目からデータが展開されます。

この2つを組み合わせ、
「数値から-1した行番目までを排除した配列から、最大1行分だけ呼び出す」
という内容を書いたことになりました。
:::
　
数値の部分を「**セル参照**」にしたいときは以下のように書く。
```Ruby:完成した関数２
=QUERY(配列,"Limit 1 Offset "&指定セル,0)
```

:::note warn
句と数値の間に半角スペースが必要となるため、セル参照する場合には「Offset」と「"」の間に半角スペースを忘れないようにしたいです。
:::
　
以上思いつきのままやった対応でした。
もっとずっと良い方法もあるのかもしれませんが、
これはパッと思いついたことを書き留める備忘録なので良しとしたいと思います😉
【Python】小数点以下の切捨て・切上げ

## はじめに

個人的なメモ、調べたことをアウトプットしています。
間違いあればご指摘の程いただけますと幸いです。

## math.floor() , math.ceil()


浮動小数点の`float` の小数点以下を切捨て・切上げするには、標準ライブラリmathモジュールの`floor()`, `ceil()` を使う。

`math.floor()`は「負の無限大への丸め」、`math.ceil()`は「正の無限大への丸め」となる。

# 小数点以下を切捨て**: math.floor()**


小数点以下の切捨てには`math.floor()` を使う。整数型の`int`が返される。

`math.floor()`は「負の無限大への丸め」を行う。

```python
import math

print(math.floor(10.123))
print(math.floor(-10.123))

#-----result--------
# 10
# -11
```

# 小数点以下を切上げ**: math.ceil()**



小数点以下の切捨てには`math.ceil()` を使う。整数型の`int`が返される。

`math.ceil()`は「正の無限大への丸め」を行う。

```python
import math

print(math.ceil(10.123))
print(math.ceil(-10.123))

#-----result--------
# 11
# -10
```

# **0への丸め: int()**


「0への丸め」には`int()` を使う。整数型の`int`が返される。

`int()`は「0への丸め」を行う。値の正負関係なく、常に0に向かって丸められる。

```python
import math

print(int(10.123))
print(int(-10.123))

#-----result--------
# 10
# -10
```

## まとめ
 `int()`での丸め込みが基本的には"丸い"なと思いますた。
[BigQuery API(V2)] Javaでサービスアカウントのメールアドレスを取得する

BigQuery API V2(Java)を使用して、
Google Cloud KMSとのやり取りに使用されるプロジェクトのサービスアカウントを
取得する方法についてご紹介します。

:::note info
APIを利用する環境の準備から始める場合や、コードを実行する際は、
[⧉[BigQuery API(V2)] JavaでBigQueryを使う](https://qiita.com/doran/items/8b7ba29672527426e88d)
を参照ください。
:::

|No||目次|
|---|---|---|
|1||[メールアドレスを取得](#1-メールアドレスを取得)|
||1|[スコープ](#11-スコープ)|
||2|[実行](#12-実行)|
||3|[レスポンスの内容](#13-レスポンスの内容)|

## 1. メールアドレスを取得
GoogleCloud KMSとのやり取りに使用されるプロジェクトのサービスアカウントを取得します。

### 1.1. スコープ
このAPIを実行するには、以下のいずれかのスコープを指定してください。
```
BigqueryScopes.BIGQUERY
BigqueryScopes.CLOUD_PLATFORM
BigqueryScopes.CLOUD_PLATFORM_READ_ONLY
https://www.googleapis.com/auth/bigquery.readonly
```
権限付与に関しては
[⧉[BigQuery API(V2)] JavaでBigQueryを使う(2.権限付与)](https://qiita.com/doran/items/8b7ba29672527426e88d#2-権限付与)
を参照ください。

### 1.2. 実行

```java
public static void main(String[] args) throws Exception{
    Bigquery bigquery = getBigquery();
    Bigquery.Projects projects = bigquery.projects();
    
    Bigquery.Projects.GetServiceAccount account = projects.getServiceAccount("プロジェクトID");
    
    GetServiceAccountResponse res = account.execute();
    System.out.println(res);
}
```
#### 1.2.1. HTTPリクエスト
GET:　https:\//bigquery.googleapis.com/bigquery/v2/projects/{プロジェクトID}/serviceAccount
が実行されます。

#### 1.2.2. クエリパラメータ
クエリパラメータはありません。

### 1.3. レスポンスの内容
#### GetServiceAccountResponse
|メソッド|戻り値|説明|
|---|---|---|
|getKind|String|リソースの種類<br>固定文字列："bigquery#getServiceAccountResponse"|
|getEmail|String|サービスアカウントのメールアドレス|

<br>
<br>
おしまい。。
find / find_by / where / find_or_create_by 各メソッドの違い

find、find_byとfind_by!、where、find_or_create_byとfind_or_create_by!など
たくさん出てきてややこしかったためまとめました。

# findメソッド
__説明__
・主キー(id)を指定しデータベースから１件のレコードを取得
・存在しない場合エラーを返す
・複数のデータ取得が可能

__使い方__
モデル.find(主キー)

__例__
```
Book.find(1)
```
```
Book.find(params[:id])
```

# find_byメソッド
__説明__
・条件を指定しデータベースから最初に見つかった１件のレコードを取得
・存在しない場合はnillを返す
・主キー以外のカラム検索も可能(カラムを指定しないとエラーになる)
・複数のデータ取得不可

__使い方__
モデル.find_by(任意のカラム名: 格納されている値)
失敗したら例外発生
モデル.find_by!(任意のカラム名: 格納されている値)

__例__
```
Book.find_by(title: "ruby")
```
```
Book.find_by(title: "ruby", body: "rails")
```
# whereメソッド
whereメソッドはどのカラムでも検索でき、複数データ取得できる良いとこどり！

__説明__
・条件を指定しデータベースからレコードを取得
・存在しない場合はnillを返す
・主キー以外のカラム検索も可能(カラムを指定しないとエラーになる)
・複数のデータ取得可能

__使い方__
モデル名.where(任意のカラム名: 格納されている値)

__例__
```
Book.where(title: "ruby")
```
```
Book.where(body: "rails")
```
```
Book.where(title: "ruby", body: "rails")
```


# find_or_create_byメソッド
__説明__
条件を指定しデータベースから最初に見つかった１件のレコーを取得、１件もなければ作成

__使い方__
モデル.fine_or_create_by(任意のカラム名: ブロック引数)
失敗したら例外発生
モデル.find_or_create_by!(任意のカラム名: ブロック引数)

__例__
```
User.find_or_create_by(first_name: "Taraou")
```

# find_byとfind_by!の違い

__説明__
・条件に一致するレコードが見つからなかった場合

find_by → nillを返す（エラーにならない）
find_by! → エラーを返す

# find_or_create_byとfind_or_create_by!の違い

__説明__
・なんらかの原因で処理に失敗した場合エラーを返す。

__例__
条件に一致するレコードが見つからず、新しいレコードを作成しようとした時に
バリデーションエラーなどになった場合

find_or_create_by → nillを返す（エラーにならない）
find_or_create_by! → エラーを返す
ArduinoUno: Lチカ

PD12 - GND
PD13 - GND
につけた　LED 2個を点滅させます。

## プログラム

```itext:Blink/Blink.ino
/*
	Blink.ino

					May/07/2024

*/
int count = 0;

void setup() {
	pinMode(12, OUTPUT);
	pinMode(13, OUTPUT);
	Serial.begin(19200);
	delay(1000);
	Serial.println("*** start ***");
	delay(500);
}

void loop() {
	Serial.println("count = " + String(count));
	digitalWrite(12, LOW);
	digitalWrite(13, LOW);
	delay(1000);

	digitalWrite(12, HIGH);
	digitalWrite(13, HIGH);
	delay(4000);

	digitalWrite(12, LOW);
	digitalWrite(13, LOW);
	delay(1000);

	for (int it=1; it<5; it++)
		{
		int time_delay = it * 1000; 
		digitalWrite(12, LOW);
		digitalWrite(13, HIGH);
		delay(time_delay);
		digitalWrite(12, HIGH);
		digitalWrite(13, LOW);
		delay(time_delay);
		}
  	count++;
}
```
初心者向け！Linuxファイルシステム階層構造の基本(1)

## はじめに

Linuxシステムの基本的な理解を深めるために、ファイルシステムの構造を知ることは非常に重要です。この記事では、Linuxの各主要ディレクトリがどのような目的で、どのように使われているのかを解説します。


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/208980/f37547f9-caad-c0f4-8e0b-32b4d8b35678.png)
ファイルシステム階層構造(https://www.linuxyogi.com/linux-directory-structure-file-system-hierarchy/)


### 1. / (ルートディレクトリ)

概要: 全てのファイルとディレクトリの起点となる場所です。
重要性: システムの構造上、最も基礎となるディレクトリです。
後から出てくる[/root]ディレクトリと、呼び名が紛らわしいので注意してください。

### 2. /bin (ユーザーバイナリ)
概要: **基本的なシステムコマンド**が保存されています（例: ls, cp）。
重要性: システムの操作に必須のコマンドが含まれるため、どのユーザーもアクセス可能です。

### 3. /etc (設定ファイル)
概要: システム全体の**設定ファイル**が格納されています。
重要性: システムの振る舞いを変更するための中核的な設定がこのディレクトリに集中しています。

### 4. /home (ユーザーディレクトリ)
概要: **個々のユーザー**のデータや設定が保管される場所。
重要性: ユーザーの個人作業空間を提供し、セキュリティとプライバシーを保つ重要な役割を果たします。

## 5. /usr (User System Resourceの略)
概要: **追加のユーザープログラムとライブラリ**が含まれます。
重要性: OSに追加でインストールされたプログラムやライブラリーなど /bin と比べると必須ではないプログラムが格納されます。またシステムの拡張性とアプリケーションのサポートに不可欠です。

## 6. /var (可変データ)
概要: **ログファイル**やメールスプールなど、変更されるデータが保存されます。
重要性: システムの動作状態を追跡し、問題解析に役立つ情報を提供します。

## 参考資料

1. Directory Structure by LinuxYogi
https://www.linuxyogi.com/linux-directory-structure-file-system-hierarchy/

1. ゼロからわかるLinuxサーバー超入門　Ubuntu対応版
https://amzn.asia/d/2PdKAwU
Suno.AIを死ぬほど使い続けた自分が達した結論

約半年になるが、これまでSUNO-AIで作曲をし続けて出した結論

https://qiita.com/EasyCording/items/6183140ff790cb92fc5a

# 歌詞が命

これは自分でも感じてきているが、歌のハマりが良い場合と、そうでない場合、原因は歌詞にあることが多い

# ()でリフレイン
(壊れそうな夢 零れそうな涙)のように、印象的な歌詞の一節をカッコ括弧で囲む
リフレインとしてループさせることができる（リフレインがあると曲に食い込みやすい）

# オノマトペで臨場感
「キラリ光る星空に ドキドキが高鳴る」のように、オノマトペを歌詞に取り入れる
臨場感が出て曲が映える

# 合いの手、雄叫び
歌詞に「心を開け!(ハァー) 希望を掴め!(うぉぉぉ)」のように、合いの手や雄叫びを入れる
曲に呼応する面白みが出る（はず）

# 同じ曲は日をまたがず
SUNO-AIで同じ曲の継続を続ける場合、日をまたがないよう一気に行うこと
日を空けると曲調が変わってしまう

# ひらがな・ローマ字
漢字の読み方でSUNO-AIが自爆することが多い
平仮名またはローマ字で歌詞を入力するとミスが減る（変換に手間取るが）

# 使い捨てアカウントを使い倒せ
通常の１日50ポイントでは完成しない。
捨てアカウントを新規登録して使いたおすこと（くれぐれもサブスクはするな）

# 結論
まだまだ言いたいことがあるが、まずは作品集を聞いてほしい

https://youtu.be/77HKoLLT3kI?si=DHTaY7uecd48Bt5a

https://youtu.be/jKdqSW5fz7M?feature=shared

https://youtube.com/clip/UgkxZ3ClB69I2hJzn045XGMLsBJMu8wik_Ts?si=aOyU_KDdYCLhXfNn

https://youtu.be/bJG4koteC-c?si=D82zjRBMekoSutZh

https://youtu.be/UTrg1yrbfBA?si=E8ENcimPsRaKY7BL
【Unity】 StringFieldやBoolFieldがない？いいえ、あります。【UIElements】

こんばんは。UnityのIMGUIに嫌気が差した皆さんはUI Elementsに移行しようとしているのではないでしょうか。
私もその末席ですが、少々引っかかったため共有しておきます。
インスペクターに`string`や`bool`型のフィールドを作るとき、` StringField`・`BoolField`がないと思ったことはありませんか？実はそれ、あります。
 それぞれ`TextField`・`Toggle`として存在します。後者はチェックボックスの形式を取ります。`value`が`true`のときにチェックが入るような描画になります。
useCallbackはどこでも利用すべきか

## useCallbackとは
関数をキャッシュするReactフックです。
第１引数に関数、第2引数に依存配列を指定し、第2引数に変更がある場合のみ関数が再度実行されます。

基礎的な事例などは[React公式ドキュメント（useCallback）](https://react.dev/reference/react/useCallback)にあります。

## どこでも利用すべきか
関数をキャッシュできるならとにかく使おう。という実装方針をとることはパフォーマンスや運用の観点で有効とは言えません。

パフォーマンスの観点では、メモ化を実施すること自体や依存配列をチェックする作業にコストがかかるため、そのコストに見合うリターンがない場合はuseCallbackの利用価値はありません。

主に利用価値が発揮されるのは以下のような場合が考えられます。

1. React.memoでラップされた重そうな描画の実施を伴うコンポーネントにpropsとして渡す場合
2. 重い処理や描画を伴うuseEffectの依存配列に設定されている場合

これらと一緒に利用せず、useCallbackを単体利用することで価値が発揮されるケースはほとんどありません。

[Reactの公式ドキュメント（useCallback#optimizing-a-custom-hook）](https://react.dev/reference/react/useCallback#optimizing-a-custom-hook)にも以下のように記載されています。

>If your app is like this site, and most interactions are coarse (like replacing a page or an entire section), memoization is usually unnecessary. On the other hand, if your app is more like a drawing editor, and most interactions are granular (like moving shapes), then you might find memoization very helpful.

重い描画処理がある場合に有効であるとのことです。

ただ、[Reactの公式ドキュメント（useCallback#optimizing-a-custom-hook）](https://react.dev/reference/react/useCallback#optimizing-a-custom-hook)にも記載がありますが、パフォーマンスへの悪影響は小さいため、どこでも利用するチームは存在しそうです。
>There is no benefit to wrapping a function in useCallback in other cases. There is no significant harm to doing that either, so some teams choose to not think about individual cases, and memoize as much as possible.

しかし、運用の観点では、useCallbackの利用によりコードの量が増え、読みにくくなるという事象が発生します。

## カスタムフックが関数を返すならuseCallbackを利用すべき
useCallbackについて調べている際にいくつかの記事を読みましたが、そのほとんどは上記のような利用するにもコストがかかるから重い描画処理がある場合にのみ利用すべきだという内容ばかりでした。

しかし、[ある記事](https://blog.uhy.ooo/entry/2021-02-23/usecallback-custom-hooks/)ではカスタムフックが関数を返す場合は常にuseCallbackを利用すべきという記述がありました。

その理由は以下のように示されていました。
>カスタムフックを作る理由は、普通の関数を作る理由と全く同じであり、すなわち責務の分離とかカプセル化です。 一度カスタムフックとして分離された以上、インターフェースの内側のことはカスタムフック内で完結すべきです。 カスタムフックを使う側はカスタムフックの内側のことを知るべきではなく、その逆も然りです。

重い処理でカスタムフックを利用することになり、useCallbackを後から追加することになった場合、それは「再レンダリングを強制する」という仕様から「再レンダリングを抑制する」という仕様変更したことになります。再利用可能性と独立性が高いカスタムフックでなかったため、後から追加する必要があったということです。仕様変更に伴い他の使用箇所への影響も考慮する必要があります。そのため、最初からuseCallbackを利用することが、再利用可能性と独立性が高いカスタムフックを作るために必要と考えられます。

## どのように運用すべきか
プロジェクトのコーディングルール等でuseCallbackの利用基準を明確にして運用した方が良いと思いました。途中から参画したエンジニアがuseCallbackを独自の観点で常に利用してしまうことや共通利用するカスタムフックをuseCallbackを利用せず後々修正が必要となることを防げます。また、Reactに精通していないエンジニアが多い環境でuseCallbackを単体利用してしまうことを防ぐことにもつながります。