OmniAICreator/Qiita-1.07M huggingface dataset:
グラフに線を引く

# はじめに
グラフを見ていると、「結局、目標に達しているの？」とか「傾向ってどんな感じ？」とか、言われることが多い。
そんなときのおすすめの機能です。

# 対象者
グラフにどこまで達しているか、目標線を出したい人
グラフの傾向がわかる傾向線を出したい人

# 作りたいグラフ
棒グラフ(累計)とか、折れ線グラフとかなど

# 使ったデータ
今回も、前回使った北海道のオープンデータを使ってみる。
商品別とか、売上とか使い勝手がよいです。

アップロードの仕方までは、前回の記事を参考にしてみてね。

https://qiita.com/hidekazu_higashi/items/95e65dcf503a0f77932c

# 目標線について
年間の売上目標に、どれくらい達成しているか、目印のようなものをつけることができたら、わかりやすいですよね。
※計画達成率を出せとか言わない。。。

ということで、棒グラフを使って作ってみた。

## グラフタイプは、「棒グラフ（累計）」を使う。
![スクリーンショット 2024-07-12 20.58.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/b6dd8a76-89c0-09d3-55a4-59b3701eaae7.png)

X軸に【決済日時】、Y軸に【金額】の合計、系列に「なし」を設定します。
X軸の単位は「週間」にしました。

![スクリーンショット 2024-07-12 20.58.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/60c0c836-c3b0-1c6c-a6a7-c96f201f26a8.png)

「５０００万が目標ってわかりやすく赤い線でも引いておいて！」とパワーポイントとか作るときには、気軽に言って行ってくる。。。

Domoでも、やってやろうではないか！

その前に、最高とか、最低とか、平均とか、邪魔なので消す。

## グリッド線を消す。
これは、「チャート線の設定」 > 「グリッド線」を選びます。
「最小値の線を削除」にチェックを入れる
「最大値の線を削除」にチェックを入れる
「計算線」を「なし」に設定する。

![スクリーンショット 2024-07-12 21.06.57.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/9fd92a32-f157-c75b-469c-2f22ee2699a6.png)

これで準備完了！

## 目標線をいれる。
目標値は５０００万としました。

これは「チャート線の設定」 > 「目盛りマーカー」を選びます。
「テキスト」に「目標」と入力する。
「タイプ」を「折れ線グラフ」にする。
「値」に「50000000」と入力する。
「色」を赤っぽい色にする。
「スタイル」を「点線」にする。

![スクリーンショット 2024-07-12 21.10.42.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/88cadc18-9ba9-b26d-40c5-6f17f882c26f.png)

## 目標線付きのグラフの完成
さあ完成しました。
![スクリーンショット 2024-07-12 21.14.22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/889cf5ea-8ce7-96e8-3c99-ba1fbabebcb8.png)


# 傾向線について
次に、いまのペースはどのいう傾向なんだろうか？上がり傾向なのか、下がり傾向なのか、わかりやすく見えるようにしたいですよね。

では折れ線グラフを準備しましょう。

## グラフタイプは、「複数折れ線グラフ」を使う。
今度は折れ線グラフでやってみたかったので、左上を選びました！

![スクリーンショット 2024-07-12 21.18.40.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/dbe92c86-27b7-eed5-bb5e-51f41560b6d0.png)

上記の「グリッド線を消す。」をやれば、下記のような感じです。
![スクリーンショット 2024-07-12 21.17.04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/33645c0d-5cd0-4f59-bd5a-a9f08d0c364a.png)

## 傾向線を入れる。
色々調べていると、Domoでは回帰線というらしいです。

「チャート線の設定」 > 「回帰線」を選びます。
「回帰直線を表示」にチェックをいれるだけ！

![スクリーンショット 2024-07-12 21.21.35.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/95f0166a-1992-1464-1884-bcc69855aa4a.png)

## 傾向線付きのグラフの完成
さあ完成しました。このままのペースで行くと、儲かりまくりです！

![スクリーンショット 2024-07-12 21.24.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3798145/e90e91b3-df23-1d5b-caa1-84d3f3d0cfde.png)

# まとめ
意外と簡単にできました。
いろいろ機能がたくさんあるので、探すのに一苦労ですが、まだまだいろいろできそうです！
JavaScriptで複数のアニメーションを連続させる方法

業務で10連ガチャのアニメーション演出をSCSS、JavaScriptで実装する機会があり、その時に使用したテクニックをまとめました。

大まかに言うと、CSSのanimationプロパティとJavaScriptのanimationendイベントを使用します。

```SCSS
.fade-in {
  animation: fadeIn 2s liner 0s forwards running;
}

.spin {
  animation: spin 2s liner 0s forwards running;
}


@keyframes fadeIn {
  0% { opacity: 0; }
  100% { opacity: 1; }
}

@keyframes spin {
  0% { transform: rotate(0deg); }
  100% { transform: rotate(360deg); }
}
```

```JavaScript
const targetElement = document.querySelector('.hoge');
hoge.addEventListener('animationend', (e) => {
    const animationName = e.animationName;
    switch(animationName){
        case 'fadeIn':
            // 要素が回転するアニメーション付与
            targetElement.classList.add('spin')
            break;
        case 'spin':
            console.log('アニメーション終了')
            break;
    }
});
```

①アニメーションを適用させたい要素を取得
②animationendイベントで各アニメーションの終了を検知
③switch文で終了したanimationNameごとに処理を振り分ける（例では次に適用したいanimationのクラス名を付与）

といったやり方により、アニメーションを連続させることができました。

③ではクラスを付与して次のアニメーションを表示させていますが、CSS側で
```CSS
.hoge { animation-play-state: paused; }
```
を予め指定しておいてから、Javacript側で

```
targetElement.animationPlayState = 'running';
```

のようにanimation-play-stateを実行中に変えてあげる、という方法でも実現できるかと思います。


※例ではquerySelectorを使用していますが、他の方法でDOMを取得した方が良いかもしれません（Vue.jsならref属性と$refsを使うなど）。
コンポーネント外でもhogeクラスを使っている場合、querySelectorやquerySelectorAllを使うと意図していないhogeクラスを持つDOMを取得する可能性があるためです。
お家CI/CD環境を組んでみた。

# はじめに

naritomoと申します。

本職はインフラエンジニアを行っています。

今回はGitlabを使用したK8SへのCI/CDを構成してみました。

いろいろアドバイスいただけると嬉しいです。

## 概要

GitLabでCICD構成を組んでみました。

## 構成図

![raspik8s-CICD構成.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1877319/00bcb03e-d8b6-540d-0e62-621b4291f2b1.jpeg)

## 参考サイト

以下のサイトがかなり参考になりました。

ありがとうございます。

https://about.gitlab.com/ja-jp/install

https://rabbit-note.com/2023/05/15/automatically-update-kubernetes-images-with-gitlab-agent

https://ossfan.net/setup/gitlab-02.html

https://blogs.networld.co.jp/entry/2022/03/10/090000

https://qiita.com/athagi/items/e212249c6f14f29db427

https://qiita.com/ynott/items/35e9492d0681ea8ac60a

https://ainoniwa.net/pelican/2022-10-22a.html

# おわりに

この記事がGitlabを扱う方の助けになればと思います。
【TypeScript】Generics で型の安全性とコードの共通化を両立

# はじめに
この記事では、TypeScript の Generics の概要について記載します。Generics を利用することで、型の安全性とコードの共通化を両立できます。

https://www.typescriptlang.org/docs/handbook/2/generics.html

# 開発環境
開発環境は以下の通りです。

- Windows11
- VSCode
- TypeScript 5.5.3

# 型の安全性とコードの共通化とは
以下の例では、関数の引数と戻り値の型を `number` と定義することで、型の安全性を担保できます。ただ、同じロジックで引数と戻り値の型を `string` にする必要がある場合、ロジックは同じで型だけが異なる関数を別途定義しなければなりません。

```index.ts
function identity(arg: number): number {
  return arg;
}
```

一方、以下の例では、引数と戻り値の型を `any` にしているので、`number`、`string` どちらの型も利用できます（型ごとに関数を定義する必要はありません）。ただ、コンパイラのチェックが行われなくなり、バグを生みやすくなります（型の安全性が損なわれます）。

```index.ts
function identity(arg: any): any {
  return arg;
}
```

したがって、型の安全性を高めるとコードの共通化が難しくなり、コードを共通化すると型の安全性が損なわれます。

# 型を変数のように扱うことで、型の安全性とコードの共通化を両立
Generics では、型を変数のように扱うことで、型の安全性とコードの共通化を両立します。
以下の例では、関数名の直後に `<T>`、変数と戻り値の型を `T` とした関数を定義しています。`T` が変数にあたります。

```index.ts
export function identity<T>(arg: T): T {
  return arg;
}
```

そして、上記の関数を利用する際、`<T>` のところで型を指定します。

```index.ts
identity<number>(1);
identity<string>("test");
```

関数の利用時に型を指定しているので、型に合致しない値を引数に渡すと、エラーになります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/318188/fa0de8f9-dc2b-cfed-3334-7f364c90e170.png)

:::note
`extends` を使うことで、Generics の型 `T` を特定の型に限定できます。

以下の例では、`T` を `string` と `number` に限定しています。
限定した型に合致しない型を指定すると、エラーになります。

```index.ts
export function identity<T extends string | number>(arg: T): T {
  return arg;
}

identity<boolean>(true);
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/318188/162930e5-c4da-4b6d-1042-fb6f79c6663f.png)


:::

このように Generics で型を変数のように扱うことで、型の安全性とコードの共通化を両立できます。

# 参考
- [Generics](https://www.typescriptlang.org/docs/handbook/2/generics.html)
- [ジェネリクス (generics)](https://typescriptbook.jp/reference/generics)
Ubuntu24.04を入れたら最初にやること

Ubuntuのメジャーアップデートが来たので入れてみました。
ほぼ個人用ですがセットアップ内容をメモに残します。

## Ubuntuのホームディレクリ名を英語にする
```
LANG=C xdg-user-dirs-gtk-update
```
デフォルトでホームのデスクトップやドキュメントといったフォルダ名が日本語になっているため、扱いやすいよう英語にします。
【参考】
https://qiita.com/peachft/items/fde3bebd356c17c1cef6

## Google Chromeをインストールする
```
wget https://dl.google.com/linux/direct/google-chrome-stable_current_amd64.deb
sudo dpkg -i google-chrome-stable_current_amd64.deb
```
ブラウザをお好みで入れます

## VLCメディアプレーヤーをインストールする
```
sudo apt update
sudo apt install vlc
```
動画再生ソフトです
映像をネットワーク経由で配信するのにも使えます

## Visual Studio Codeをインストールする
アプリセンターでcodeと検索
出てきたVisual Studio Codeをインストール
### 拡張機能
Japanese Language Pack
PlantUML

PlantUMLは所定の形式のテキストから自動でUML図を生成してくれる便利なソフトです

PlantUMLのためにJavaをインストールする
以下のコマンドでバージョン候補が表示されます

```
apt search openjdk | grep openjdk
```
openjdk-21-jdkを選択
```
sudo apt update
sudo apt install openjdk-21-jdk
```
【参考】
https://qiita.com/studio_meowtoon/items/4d11e94a2389758759cd

VS Code上でAlt+Dキーでプレビュー図が表示されるようになりました

## Gitをインストールする
### Git
```
sudo apt install git
```
```
git --version
```
言わずと知れたバージョン管理ソフト


### Githubデスクトップ
```
wget -qO - https://apt.packages.shiftkey.dev/gpg.key | gpg --dearmor | sudo tee /usr/share/keyrings/shiftkey-packages.gpg > /dev/null
sudo sh -c 'echo "deb [arch=amd64 signed-by=/usr/share/keyrings/shiftkey-packages.gpg] https://apt.packages.shiftkey.dev/ubuntu/ any main" > /etc/apt/sources.list.d/shiftkey-packages.list'
sudo apt update && sudo apt install github-desktop
```
Gitの操作にGUIがないときつい人なので。Windows, Mac, Linuxと幅広く対応しているため重宝してます

アプリ一覧にGithub Desktopが追加されたことを確認

【参考】
https://gist.github.com/berkorbay/6feda478a00b0432d13f1fc0a50467f1

## Dockerをインストールする
公式のドキュメントに従います
https://docs.docker.com/engine/install/ubuntu/

dockerのaptリポジトリのセットアップ
```
# Add Docker's official GPG key:
sudo apt-get update
sudo apt-get install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc

# Add the repository to Apt sources:
echo \
  "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu \
  $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
  sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt-get update
```
dockerパッケージのインストール
```
sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
```
動作確認
```
sudo docker run hello-world
```

root権限無しで動かせるようにする
```
sudo groupadd docker
```
```
sudo usermod -aG docker $USER
```
更新
```
newgrp docker
```
確認
```
docker run hello-world
```

## 最後に
初投稿で拙い記事にはなってしまいましたが、お役に立てれば幸いです。
Webエンジニアの学習ロードマップが知れるサイト

エンジニアのみなさま、日々の学習本当にお疲れ様です！
また本記事まで足を運んでいただき本当に感謝です。
約2分程度で読めるので最後まで読んでもらえると幸いです。

# はじめに

「Webエンジニアを目指したいが、何から手をつけていいか分からない」

「いろんな人が学習ロードマップの情報提供をしているが、どれに手をつけるか判断に迷う」

こんな悩みを抱えている方の一助になれば幸いです...！

# 結論

https://roadmap.sh/

こちらのサイトになります。

![スクリーンショット 2024-07-13 23.07.41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3744730/17503627-128b-340b-ec2a-7c7a59565b31.png)

自分が学習したい分野を選択すると、その分野のロードマップが書かれています。
最近では「言語専用」のロードマップも書かれているため、かなり充実したサイトになってきた印象です。

それでは、試しに「Backend」のロードマップを見てみましょう。

# 学習ロードマップ｜Backend

こんな感じです。

![20240713.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3744730/af6cead5-1abd-7f22-0df1-42deb62cdfae.gif)

黄色塗りのフォームが「仕組み」や「概念」が書かれたもので必ずチェックしたい内容になります。
上記フォームに紐づいたフォームには色付きのチェックマークがついてます。

:::note info
紫：Personal Recommendation / Opinion（サイト内の推薦 / 意見）
緑：Alternative Option / Pick this or purple（紫の代替案）
グレー：Order not strict / Learn anytime（時間があるときに学習）
:::


基本的には紫を学習しつつ、ご自身の環境や学びたい言語に合わせて緑を選択する様な流れになります。

試しに「Pick a Language」にある「JavaScript」を選択してみましょう。

![スクリーンショット 2024-07-13 23.40.41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3744730/cc039d84-cc35-6216-8814-0561b7a0c514.png)

こんな感じで各項目に合わせて「どんな事を学習する必要があるのか？」をまとめてくれています。
ここで難点なのが全て英語で書かれています...
そのため、学習ロードマップの全体像はこのサイトで確認をして、学習は公式ドキュメントやYouTube、日本の記事を見ながら順番に対応していくが良いかなと考えます。

# さいごに

改めてみるとWebエンジニアになるためには広範囲で学習することが必要です。

これからWebエンジニアを目指しているみなさま。「めちゃくちゃ学習することあるやん...」と思われた方も多いかと思いますが、悲観せずにやっていきましょう！

私はエンジニアに転職して4年目に突入しましたが、このサイトに書かれている内容全てを語れる訳ではありません...
しかしながら、何とかここまで微力ではありますが生き延びてやってこれてます。
自分を信じてコツコツ取り組んでいけば理解も深まりどんどん楽しくなってくるはずです。
一緒に頑張っていきましょう！

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


# おまけ

唐突ですが弊社のご紹介もさせてください。

▼ コーポレートサイト

https://prum.jp/

▼ Wantedly求人

https://www.wantedly.com/projects/626662

弊社メンバーは学習した内容を日々Qiitaの記事にアウトプットしております。
弊社にご興味のある方、まずは求人を見てみてください！
ご応募お待ちしておりますー！
ABC362回答メモ

# 0.はじめに
　最近下降気味の成績を挽回するべく参加。
　結果はC問題すら解けない惨憺たる成績。
　C問題も振り返ればそこまで難解ではなく
　レートは-38で737と茶色安定のこの頃です。


# 1.A - Buy a Pen
　A問題ながらちょっとひねった問題。
　といっても、素直に言われた通りの実装すれば
　迷うことはありませんでした。
　Cで指定される色以外の2色の値段のうちminで小さい方を
　出力して終了として、ACでした。

　https://atcoder.jp/contests/abc362/submissions/55513491


# 2.B - Right Triangle
　後から解説をみたら、三平方の定理を使って直角を求める方法が
　紹介されていましたが、コンテスト時は思いつきませんでした。
　
　昔使った(ググって拾って来た)、3点の角度を求める方法で
　角A～Cの角度を求めていずれかが90°だったらYes
　そうでなければNoを出力して終了としました。

　https://atcoder.jp/contests/abc362/submissions/55530776


# 3.C - Sum = 0
　最初に建てた解答方針が間違っていたため、１時間たっても
　解けず惨敗しました。
　
　【間違った考え方】
　　1.整数の組を以下の3つに分ける
　　　L）Lが0より大きい
　　　R）Rが0より小さい
　　　M）LとRの間に0が含まれる
　　2.Xを作成する際、LはL[i]、RはR[i]を選択する場合が
　　　0に近づくので、その場合の合計値を
　　　Mの値で調整する
　　https://atcoder.jp/contests/abc362/submissions/55566280
　
　コンテスト時は上記考えで行けると思い込んで四苦八苦していましたが
　今思えば以下のようなケースであっさりだめになりました。
　2
　-2 -1
　2 3

　コンテスト時に気づけばよかったのですが嵌っているときは
　そううまくいかず、時間切れ。
　解説をよんだらもっと単純な方法で解決できました。
　【考え方】
　　1.LとRをリストLisに格納しつつ、LとRをLSとRSに集計
　　2.LSが0より大きいまたは、RSが0より小さい場合は条件を満たすXは作れないのでNo
　　　それ以外はYesを出力
　　3.LS(XにすべてLを採用した場合のXの合計値)をもとにiを0～N-1の間以下の処理をしていく
　　　→X(以下の処理ではリストans)の合計が0となるまでXにR[i]を格納していく
　　　-1.LSが0の(もうXにR[i]を格納必要がない)時、ansにL[i]を格納
　　　-2.LS+(R[i]-L[i])が0より小さい時（XのL[i]をR[i]に変えてもXの合計が0にならない時）
　　　　 ansにR[i]を格納し、LSにR-Lを加算
　　　-3.LS+(R[i]-L[i])が0より多くなる時（XのL[i]をR[i]を変えたらXの合計が0以上になる時）
　　　　 ansにL[i]+LS*-1を格納し、LSに0をセット
　　4.ansを出力して終了
　　

　https://atcoder.jp/contests/abc362/submissions/55589741


以上
大吉祥寺.pm のメモを markdown AI にまとめてみた

https://qiita.com/official-events/142fdd0d69ff6bb2d547

> markdown AI を使った記事を投稿しよう！

> https://mdown.ai/ にてサインインください。
> 必要なのは Googleアカウントのみ で 無料 でご利用できます。

とのことで、シンプルにちょっとした記録を残すのにちょうどいいのでは、と markdown AI を使ってみた。

## 大吉祥寺.pm

[大吉祥寺.pm の資料](https://mdown.ai/content/720032a6-a3e8-4c75-b603-153ddcbb975c)

## markdown AI を使った感想
- シンプル
- スマホでポチポチ記録していた内容を、PC でも後から見るとか、本当に、ただノートを取るだけのことならこれで十分

以上です～
ABC362 日記

　新人競プロerの山田です。
　ABCDEの5完、2120位、perf1252、レーティング変動は963→999(+36)でした。

### [A問題](https://atcoder.jp/contests/abc362/tasks/abc362_a) [B問題](https://atcoder.jp/contests/abc362/tasks/abc362_b)
　うん。（提出時刻はそれぞれ2分47秒、7分23秒 ノーペナ）

### [C問題](https://atcoder.jp/contests/abc362/tasks/abc362_c)
　数列の合計をゼロにする問題。難なく考察完了して21時16分48秒にAC。（所要時間9分）
　ただツイッターを見ているとここで苦戦した人が意外と多かった。山田は直感的に思いつくことができたけれど、調子の悪いときには思いつかないかもしれない。
　直感的に思いつけなかった場合、「上界、下界を考える」というパターンを思い出すことが求められる。でもABCのC問題でそれは厳しい。山田は詰まりそう。脳みそのすぐ出てくる領域にその発想がない。
 
### [D問題](https://atcoder.jp/contests/abc362/tasks/abc362_d)
　ただの重み付き有向グラフ最短距離問題に落とし込む問題。
　即実装。Mへの入力を忘れたりして少しバグらせたが難なく直していって、サンプルケースもすべて合って提出した(21:31:54)。しかしなんとここでTLEして1ペナ。
　TLEの理由は、ダイクストラ法の実装ミス（**確定済み頂点をメモしていなかった**）。このしょうもないミスが今回の一番の反省。
　ただこのデバッグはすぐに終わって21:34:52 AC。（所要時間18分）

### [E問題](https://atcoder.jp/contests/abc362/tasks/abc362_e)
　等比数列の部分列が何個ありますか問題。
 
　考察に時間がかかった。dpなどいろんな解法を考えては捨てていた。
　初項と公差をi,jとして全探索する方法を考えたが、制約を見て、実行時間的に不可能であることを知り断念。そこで無駄な探索を減らすためにはどうするか考えることで正攻法にたどり着いた。あるA[i]とA[j]を選んでそれぞれを第1項、第2項とすれば、初項と公差が確定するため、探索すべき初項と公差の組み合わせはA[i]とA[j]の組み合わせの数しかない(N<=80だからめっちゃ少ない)。
 　**自明に間に合わないアホな全探索から正攻法を思いつくこともあるんだな。** 初項と公差の全探索という発想を脳内で0秒とかで切り捨てていたら思いつくことができなかった。
　固定した後は、dpでどうにかする。（本番中は、dpでどうにかなるか……？　なるよな……？　それ以外に解法思いつかないしって感じだった）

　これで実装開始したのが22時ちょい前だったと思う。
　第1項第2項を固定した上で、dpは「dp[i][j] = 数列Aのj項目まで考慮したときに、項数iの等比数列が何通りあるか」として実装。

　サンプルケースも全部合ってたので22:15:01に提出したがWAとなった。
　コードテストで入力をいろいろいじっていって、数列Aを「0 0 0 0 0」としたときに出力がおかしくなった。そこからバグの原因を究明。
　バグの原因はただのdpの遷移ミスだった。22:23:44にAC。（所要時間49分）

　二次元dpの遷移って頭の中でやるとしんどい。だからといって計算用紙に書くのも時間かかり、リスクリターンが合わない。（サンプルケースでおかしくなった場合は書くけど）
mindの研究 その84

# 概要
mindが、謎なので調べてみた。
練習問題やってみた。

# 練習問題
お嬢様ぽく、fizzbuzzを書け。


# サンプルコード

```
お入は　入れると　等価。

メインとは
　世１５は　変数よ
　世５は　変数よ
　世３は　変数よ
　９９を　回数指定して
　　回数を　１５で　剰余を　世１５に　お入
　　回数を　５で　割余を　世５に　お入
　　回数を　３で　割余を　世３に　お入
　　世１５が　０に　等しい
　　ならば
　　　「FizzBuzz」を　表示するのよ
　　さもなければ
　　　世５が　０に　等しい
　　　ならば
　　　　「Buzz」を　表示するのよ
　　　さもなければ
　　　　世３が　０に　等しい
　　　　ならば
　　　　　「Fizz」を　表示するのよ
　　　　さもなければ
　　　　　回数を　数値表示するのよ
　　　　つぎに
　　　つぎに
　　つぎに
　　「 」を　表示するのよ
　繰り返すのよ
。




```

以上。
Markdown の Frontmatter 記載、Scaffdog に任せよう

## この記事の概要

記事ページのコンテンツを Markdown で管理することはよくあると思います。
なおかつ、Frontmatter にメタ情報を書くこともよくあると思います。

ただ私がアホすぎるがゆえに、Frontmatter に何を書いていたか忘れたり、正しいプロパティ名を忘れたりすることが多いです。

というわけで Scaffdog を使って記事の雛形を生成する流れを記事にしました。

## インストールや初期化

```sh
npm install --save-dev scaffdog
```

```sh
npx scaffdog init
# 設定ファイルの名前を求められる。ここでは article とする
```

これで`.scaffdog`ディレクトリに`config.js`と`article.md`が生成されました。

以降は`.scaffdog/article.md`を編集していきます。

## 実現したいこと

設定を追加する前に、最終的に実現したいことを整理しておきます。

- 記事の slug を入力すると`src/content/article`に`入力したテキスト/index.md`が作成される
- 記事タイトルを入力すると Frontmatter の`title`にテキストが適用される
- ファイルを作成した日付が Frontmatter の`date`に`YYYY-MM-DD`の形式で適用される
- draft かどうかを聞かれ、Yes/No にあわせて Frontmatter の`draft`に true/false が適用される

## 完成形

~~~markdown
---
name: "article"
root: "src/content/article"
output: "."
ignore: []
questions:
  slug: "slugは？"
  title: "記事のタイトルは？"
  draft:
    confirm: "下書き？"
    initial: true
---

# `{{ inputs.slug }}/index.md`

```markdown
---
title: "{{ inputs.title }}"
date: {{ date "YYYY-MM-DD" }}
draft: {{ inputs.draft ? "true" : "false" }}
---
```
~~~

そんなに難しいことはしていないのですが、少しつまづいた箇所があったのでその部分だけ解説します。

## 今日の日付を入れる

ビルトインのヘルパーに`date`があります。

https://scaff.dog/docs/templates/helpers#date

他のヘルパーは値と関数をパイプ`|`で繋いでいたので、date もそうなのかと思いましたが、違いました。

こちらにあるように、当日以外の日付でフォーマットすること自体ができないようです。

https://github.com/scaffdog/scaffdog/blob/b8d4f20be6ba889f3bb6d3e0f14a6e3640b35821/packages/%40scaffdog/engine/src/helpers.ts#L218-L221

## draft の true/false

最初、以下のように書いていました。

```
  draft: {{ inputs.draft ? true : false }}
```

しかし、これだと Yes でも No でも何も Frontmatter に記載されません。

公式ドキュメントにあるように、`{{}}`の中が true でも false でもアウトプットは空になってしまいます。

https://scaff.dog/docs/templates/template-engine#basic-syntax

よく考えれば当たり前な気がしますが、Frontmatter 内で真偽値として記載しているとは言え、あくまで文字列です。

```diff
- draft: {{ inputs.draft ? true : false }}
+ draft: {{ inputs.draft ? "true" : "false" }}
```

これで期待通りになりました。

## 実際に使う

記事を作成するにあたり、ターミナルで次のコマンドを実行します。

```sh
npx scaffdog generate article
```

すると、先ほど設定した内容が聞かれますので、答えていきます。

```sh
ℹ Output destination directory: "src/content/article"        
? slugは？ test
? 記事のタイトルは？ テスト記事です
? 下書き？ (y/N) Yes
       
🐶 Generated 1 file!                                                            
     ✔ src/content/article/test/index.md
```

生成された Markdown ファイルも問題ありません。

```markdown:src/content/article/test/index.md
---
title: "テスト記事です"
date: 2024-07-14
draft: true
---
```
rex0220 横並びプラグイン

kintone のテーブルやグループを横並びに表示するプラグインです。
テーブルを横に並べて、効率的に作業が進められます。

横並びプラグインの特徴
・テーブルやグループなどを横並びに表示できます。
・PC 環境のみ対応

Ver.3
・テーブル内項目の横幅が設定値を動的に超える場合に、横並びが解消される問題の対策
　※ファイル項目名や文字列項目で長い文字列の折り返し無しなど
　横幅のマージンとして 800px を設定し、動的に横幅が長くなっても 800px までの超過に対応

- 参考
    - [rex0220 横並びプラグイン 応用例1](https://qiita.com/rex0220/items/78e14cf99e4dae981c15)
    - [rex0220 横並びプラグイン 応用例2 年カレンダー](https://qiita.com/rex0220/items/985cdf23dd00855ce578)
    - [rex0220 横並びプラグイン 応用例3 月カレンダー](https://qiita.com/rex0220/items/146a601aff6cb5de1c1a)

# 概要

詳細画面と編集画面で、テーブルやグループを横並びに表示できます。
テーブルやグループの横の無駄なスペースを活用できます。
画面の行位置とプラグイン設定で簡単に配置を変えることが出来ます。

※DOM 操作を行う JavaScript カスタマイズ、CSS カスタマイズ、プラグインと競合して、動作しない場合があります。

動作しない例 
・タブ表示プラグイン
　タブ表示が不正・横並びの位置がずれる等
・ちょっと便利なプラグイン
　F21 行の追加・削除ボタンを左に表示：複数テーブルのボタンが左に固定表示される等

- 編集画面

![2024-07-14_04h08_24.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/6537ee44-ba83-d66c-aaa9-3378dc109a68.png)

- 詳細画面

![2024-07-14_04h08_45.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/2fc04315-6ea2-3c54-99c4-dcea9ddbe8f9.png)

# 操作例

![2024-07-14_04h15_44.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/5f90e6ab-e625-6395-7eb9-33e03a44fe9f.gif)

# アプリ設定

アプリ設定は、横並びにするテーブルやグループを上下に並ぶように配置します。

![2024-07-14_04h50_17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/1ea7ee20-0a41-938b-7c43-b26e483b3c1a.png)

# 「テーブル名を表示しない」指定時の表示ズレ

テーブルの「テーブル名を表示しない」をチェックすると、横並び表示した場合に上下がズレます。
横並び表示する場合は、テーブル名を表示するように設定してください。

![2024-07-14_11h04_20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/7fb2444e-b75c-698a-ea05-d3d37b4f6723.png)

# フィールドのアクセス権について

項目にアクセス権を設定して、1行内の項目がすべて閲覧権限の無い項目になると、画面から1行分表示されなくなり、横並び設定がズレます。
行内にダミーの表示を配置して、1行分の表示が無くならないようにしてください。

![2024-07-14_09h48_41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/e6870a71-6269-fd61-b046-f5cff501c043.png)


# 横並びプラグイン設定

- プラグイン有効
- タイプ： ROW, SUBTABLE, GROUP
- ラベル
- フィールドコード
- 表示項目
- 運用環境に反映
- 「保存する」
- 「キャンセル」
- プラグイン設定ダウンロード
- プラグイン設定アップロード

行・テーブル・グループ単位に連続してチェックされた部分が横並びに表示されます。
複数の横並びを連続して設定できませんので、罫線などを配置して横並びを区切ります。

※罫線「HR」で、横並びを区切っています。

![2024-07-14_10h10_20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/36199da7-eec1-022d-acb6-13e70dee0a90.png)


# アプリフォーム変更時のプラグイン設定

画面に項目を追加した場合は、プラグインの再設定が必要です。
変更内容によって、ROW タイプの選択内容が引き継がれない場合もあります。
これは、ROW タイプの設定は特定のユニーク値を待っていないためです。
「ROW タイプが非選択になりました。」のアラートが表示された場合は、ROW タイプの再設定が行ってください。

テーブルとグループについては、フィールドコードを識別して選択内容を引き継ぎます。

![2024-07-14_04h30_14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100572/be842cc9-682d-9548-bc21-90d3406e3771.png)
React の useId っぽいことが実現できる Simple scope

## この記事の概要

React では v18 から [useId](https://react.dev/reference/react/useId) という hook が追加されています。

アクセシビリティのための id 生成や、同一ページ内の違う要素間での id 被りを気にしなくて良くなる機能です。

非常に便利なのですが、React の機能なので React でしか使えません。

しかし、Vite を使っていれば Vue でも Svelte でも関係なく解消できるのが Simple scope です。

https://simple-stack.dev/scope

使い方について、Astro を例にして説明した記事です。

## 使い方

まずはインストールします。

```sh
npm i vite-plugin-simple-scope
```

次に`src/env.d.ts`に型を追加します。

```diff_typescript
  /// <reference types="astro/client" />
+ /// <reference types="vite-plugin-simple-scope/types" />
```

その上で、`astro.config.mjs`でプラグインを適用します。

```diff_javascript
  import { defineConfig } from "astro/config";
+ import simpleScope from "vite-plugin-simple-scope";

  export default defineConfig({
+   vite: {
+     plugins: [simpleScope()],
+   },
  });
```

後は、各ページで使用するのみです。

```jsx:some-page.astro
---
import { scope } from "simple:scope";
---

<form>
  <label for={scope("email")}>Email</label>
  <input id={scope("email")} name="email" />
</form>
```

これにより、ランダムな id が生成され、コンポーネント間の被りを気にしなくて良くなります。

## 補足

フレームワークごとで plugin 指定の方法が微妙に違いますが、それ以外で使い方に違いはありません。
暗号資産ビットコイン(BTC)のフルノードを構築する方法

## 要　旨
暗号資産ビットコイン(BTC)のフルノードを構築する方法(CLI)について記述します。
## 実行環境等
VPS:KAGOYA VPS
OS:Ubuntu22.04LTS
CPU/メモリ:4コア/4GB
ストレージ:800GB SSD
料金　126円/日、3,520円/月(2024.7.12時点)
同期開始:2024.7.12(金)04:00
同期完了:2024.7.14(日)03:00
同期に要した時間:47時間00分
使用ストレージ容量:642GB
## 実施要領
アップデート
```linux
apt update
```
ウォレットのインストール
```linux
wget https://bitcoincore.org/bin/bitcoin-core-26.2/bitcoin-26.2-x86_64-linux-gnu.tar.gz
```
展開する。
```linux
tar -xzvf bitcoin-26.2-x86_64-linux-gnu.tar.gz
```
不要になったファイルの削除
```linux
rm bitcoin-26.2-x86_64-linux-gnu.tar.gz
```
ディレクトリの移動
```linux
cd bitcoin-26.2/bin
```
コマンドをインストールする
```linux
install -m 0755 -o root -g root -t /usr/local/bin *
```
bitcoindの起動
```linux
bitcoind
```
起動を確認したら(1分経過したら)、一旦停止させる。
ctr + C
~/bitcoin-26.2/bitcoin.confを編集する。
```linux
vi ~/bitcoin-26.2/bitcoin.conf
```
以下を記述して、保存する。
```linux
[main]
mainnet=1
daemon=1
server=1
rpcuser=rpcuser
rpcpassword=rpcpassword
rpcport=8332
gen=1
genproclimit=-1
disablewallet=0
```
bitcoin.confファイルを~/.bitcoin/ディレクトリへ移動させる。
```linux
mv ~/bitcoin-26.2/bitcoin.conf ~/.bitcoin/
```
再度bitcoindを起動させて、同期させる。
```linux
bitcoind
```
同期状態の確認。
```linux
tail -f ~/.bitcoin/debug.log
```
## 結　言
今回は、暗号資産ビットコイン(BTC)のフルノードを構築する方法(CLI)について記述しました。
Pythonのクラスされた生成されたオブジェクトが破棄されるタイミング：オブジェクトの寿命とガーベジコレクションの真実

# Pythonオブジェクトの寿命：スコープとガーベジコレクションの真実

Pythonでクラスからオブジェクトを作るとき、「スコープから外れたら消える」と思っていませんか？ 実は、必ずしもそうとは限りません！ オブジェクトの寿命を握るのは **参照カウント** と **ガーベジコレクション** です。

## スコープから抜けたら破棄されるんじゃないの？

一見、スコープとオブジェクトの寿命は関係ありそうですが…
以下は、スコープを抜けた場合のオブジェクト破棄の単純な例です。

```python
class SomeClass:
    def __init__(self):
        print("Instance created")

    def __del__(self):
        print("Instance destroyed")

def func():
    obj = SomeClass()  # SomeClassのオブジェクトを作成
    print("Inside the function")

func()
# "Instance created"
# "Inside the function"
# スコープを抜けたため、オブジェクトも破棄される
# "Instance destroyed"
```

上の例ではスコープから抜けたためにオブジェクトが破棄されるようにみえます...

## 参照カウントとガーベジコレクションの舞台裏

実は、オブジェクトは 「参照カウント」という値を持っています。これは、そのオブジェクトを「参照している」変数やデータ構造の数です。


参照カウントが 0 になったら、オブジェクトはもはや必要ないと判断され、 ガーベジコレクション によってメモリから解放されます。以下は参照カウントを追跡した例です。

```python
import sys

class SomeClass:
    def __init__(self):
        print("Instance created")

    def __del__(self):
        print("Instance destroyed")

obj = SomeClass()
print(sys.getrefcount(obj))  # 出力: 2 (objとsys.getrefcountの引数として渡されているため)

another_ref = obj
print(sys.getrefcount(obj))  # 出力: 3 (another_refが新たに参照)
print(sys.getrefcount(another_ref))  # 出力: 3

del another_ref
print(sys.getrefcount(obj))  # 出力: 2 (another_refを削除)

del obj
# "Instance destroyed" (objが削除され参照カウントが0になる)
```

参照カウントが 0 になったら、オブジェクトはもはや必要ないと判断され、 ガーベジコレクション によってメモリから解放されます。

## さよならオブジェクト！ `__del__`メソッドで最後の挨拶

オブジェクトが消える瞬間に何か処理を実行したい場合は、 `__del__`メソッドを定義します。ただし、`__del__`メソッドの呼び出されるタイミングは、ガベージコレクタ次第です。

```python
class ResourceManager:
    def __init__(self):
        self.resource = "Important data"
        print("Resource acquired")
    
    def __del__(self):
        print(f"Releasing resource: {self.resource}")

# オブジェクトの作成と破棄
rm = ResourceManager()
del rm
# この時点で"Releasing resource: Important data"が出力されるかもしれないが、保証はない

print("Program continuing...")
# プログラムの終了時に__del__が呼ばれる可能性もある
```
`__del__`メソッドの呼び出しのタイミングは保証されません ! リソースの解放などの重要な操作に使用すべきではありません。その代わりに、`with`文を使用することをお勧めします。

## `with`文との比較: リソース管理のより良い方法
`__del__ `メソッドは、オブジェクト消滅時の処理を定義できますが、ガーベジコレクションのタイミングは予測できません。ファイルやネットワークなど、確実にリソースを解放したい 場合は、 `with`文 を使いましょう。

```python
class DatabaseConnection:
    def __init__(self):
        print("Connecting to database")
    
    def __enter__(self):
        return self
    
    def __exit__(self, exc_type, exc_val, exc_tb):
        print("Closing database connection")
    
    def query(self):
        print("Executing query")

# with文を使用した場合
with DatabaseConnection() as db:
    db.query()
# ここで確実にデータベース接続が閉じられる

print("After with block")

# with文を使用しない場合
db = DatabaseConnection()
db.query()
# ここでデータベース接続が閉じられる保証はない

print("After normal usage")
```

上記の例では、`with`ブロックに入ったときに`__enter__`メソッドが呼ばれ、ブロックを抜けるときに`__exit__`メソッドが呼ば出され、リソースが解放されます。これにより、例外が発生した場合でもリソースの適切な解放が保証されます。

### まとめ

Pythonのオブジェクトの寿命は、スコープだけでなく、参照カウントとガーベジコレクションによって管理されています。 `__del__` メソッドで最後の処理を定義することもできますが、リソースの確実な解放にはwith文を使いましょう！
【Drupal】TaxonomyがなんでCoreに入ってるか真剣に考えました

「TaxonomyTerm便利ですよね。」って導入をいつもだったらするんですが、今回はできません。

なぜなら私は、TaxonomyTerm を Core から外してほしいと思っているから。

この冒頭で「何言ってるの？」って感じた方。TaxonomyTermの強み言えますか？

## お前誰？ってならないためにも

素人じゃないです。
Drupal Triple Certified を制覇しています。

[アクイア認定 - Drupal Triple Certified](https://certification.acquia.com/user/18866)

## TaxonomyTerm 概要

> Taxonomy, a [core](https://www.drupal.org/glossary#core) module, gives your sites use of the organizational keywords known in other systems as categories, tags, or metadata. It allows you to connect, relate and classify your website’s content. In Drupal, these terms are gathered within "vocabularies". The Taxonomy module allows you to create, manage and apply those vocabularies.

https://www.drupal.org/docs/user_guide/en/structure-taxonomy.html

要は、コンテンツの分類・カテゴライズを目的とした Entity です。

## 忖度なしで強み紹介

### Entityである

EntityForm、EntityView、URL発行、Fieldable であるといった基本的なEntityの機能を保有しています。

### フリータギング

公式Docに書いてありました。

### ウェイトを標準で保持できる

管理画面から並び替えを行うことができます。

### 階層構造を表現

先程の並び替えに通ずるんですが、階層構造の表現ができます。GUIも提供されています。

### Workflowが使える
たしか、D10.3 からだったと思います。Workflowのシステムに対応しています。

### ViewsのExposedFilterの選択プルダウンが標準提供されている
Entity参照フィールドの選択プルダウンって、実はTaxonomyのみしかサポートされてないんですよね。

## 「忖度なしで強み紹介」 → ほんとに強みなのか確認

### Entityである
強みというか、普通のことですよね。Drupalで Entity じゃないデータを扱うのはデメリットでしかない。

### フリータギング
TaxonomyTermじゃなくても標準でサポートされています。Taxonomy Term独自のものじゃないです。

### ウェイトを標準で保持できる
これは一見強みなんですが、弱みでもあります。
例えば、「Views:1ではこの並びをしたい」「Views:2ではこの並びをしたい」という要件が満たせません。

### 階層構造を表現
これも先程と同様。条件に依る対応ができないです。
#### 一応…。
[DraggableViews](https://www.drupal.org/project/draggableviews)というモジュールがあります。

最近アプデが入って階層構造を表現できるようになりました。

もちろん、以下の要件も余裕で満たせます。
> 例えば、「Views:1ではこの並びをしたい」「Views:2ではこの並びをしたい」という要件が満たせません。

### Workflowが使える
タグへのWorkflow？？
いつ使うんですか？
Nodeじゃだめなんですか？

### ViewsのExposedFilterの選択プルダウンが標準提供されている
唯一の強みだと思います。
でもDrupalは、PluginAPIのシステムが強力なのでコード実装をしたとしても正直そんなにコストかからない。

## いかがでしょうか？
TaxonomyTermが持つ独自で持つ機能って**どれも力不足**だと思います。
2年間Drupalだけをやってきましたが、それをCoreにいれる意図が私はいまいちわかっていません。

:::note warn

#### 並び替えをしたいためだけのTaxonomyTermならその決断は悪手
#### フリータギングをしたいためだけのTaxnomyTermならその決断は悪手
#### 「タグづけしたいため、カテゴライズしたいため」だけのTaxnomyTermならその決断は悪手
:::

#### 例えばですが…。
ディレクター：「並び替え要件はマストなんだよねぇ。」
エンジニア：「プレーンなカスタムエンティティとDraggableViewsで対応します。」

がきれいだと思います。拡張性も高い。

## 「とりあえずTaxonomyTermを使う。」はほんとにやめてほしい

結構必死なんですが、理由もちろんあります。

以下のフィールド勝手についてきますよね。いらないデータは極力排他すべきです。

- Author
- 投稿日時
- 更新日時
- ウェイト

また、以下の機能も勝手についてきますよね。
- EntityView
- リビジョン

これがオプションなら全然ありです。

## まとめ
全否定というわけではありません。
**ブログに特化したモジュール**と捉えればめちゃくちゃ便利だと思います。手っ取り早いので。


でもDrupal選定した理由って、CMSを構築したいってことですよね？
であれば、TaxnomyTermを積極的に使う理由ってさほどないように感じています。

## 参考
https://www.drupal.org/docs/glossary#core

https://www.drupal.org/docs/user_guide/en/structure-taxonomy-setup.html

https://www.drupal.org/docs/8/core/modules/taxonomy/taxonomy-module-overview
Javaで「文字列の中の正規表現パターンとマッチする部分を置換する」の動作を確認してみた

# 概要

Javaで「文字列の中の正規表現パターンとマッチする部分を置換する」の動作を確認してみました。
以下のページを参考にしました。

https://www.javadrive.jp/start/string/index21.html

# 実装

以下のファイルを作成しました。
```JSample21_1.java
class JSample21_1{
  public static void main(String[] args){
    String regex  = "aA|Aa|aa";
    String str = "AA BB aA Aa CC aa";

    System.out.println(str.replaceFirst(regex, "AA"));
    System.out.println(str.replaceAll(regex, "AA"));
  }
}
```

以下のコマンドを実行しました。
```
$ javac JSample21_1.java 
$ java JSample21_1 
AA BB AA Aa CC aa
AA BB AA AA CC AA
```

# まとめ

何かの役に立てばと。
公開鍵暗号方式をCLIで試してみた

## はじめに
公開鍵暗号方式は言葉の意味としては知っていましたが、実際に流れを理解しながら実践したことがなかったので、今回やってみました。

## 公開鍵暗号方式とは
公開鍵暗号方式とは、公開鍵を暗号化に使用し、秘密鍵が復号に使用する暗号方式。
公開鍵を不特定多数の人に共有できるため、大人数のデータのやりとりに向いています。

## 公開鍵暗号方式をCLIで実践
### 鍵ペアの作成
- 秘密鍵の作成
OpenSSLを使用してRSAアルゴリズムによる秘密鍵を生成し、AES256で暗号化して private_key.pem というファイルに保存します。
pass phraseが求められるので任意の文字を入力します。あとで、複合する際に使用します。
```sh
$ openssl genpkey -algorithm RSA -out private_key.pem -aes256

..+.+..+......................+...+..+.+.....+......+....+......+.....+...+......+......+.+..+...+..........+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*......+.+......+.........+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*...+......+.........+.+.....+........................+......+....+............+...+........+.......+..+...............+......+.......+.....+............+....+..............+.+.........+........+....+..............+........................+...+...+....+.....+...+...+......+.+...+............+...+.........+...+.....+......................+......+...........+......+.......+.....+.......+.....+...+.+............+..+.+..+...+....+.....+..................+...+.......+...+..+.............+..+....+...........+.........+...............+...+.+.....+............+.........+.+.....+.......+..+...+.......+.....+....+.....+.+......+..+......+....+...+...+.....+......+...+.+......+...+............+...+..+.........................+...........+...+.......+.....+....+...+.....+.+...........+......+....+.....+......+.......+........+.............+.........+......+.....+....+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
.....+...+...............+...........+....+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*.......+...+..+...+......+......+.............+.....+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++*..+.....+.+..+...+...+.+......+.....+.............+.....+.........+.+......+...+..+...+.+.................+.......+...+...+...........+.+........+.+.....+.+.....+....+......+.....+..........+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Enter PEM pass phrase:
Error writing key
```
- 公開鍵の作成
作成したRSA秘密鍵から対応する公開鍵を抽出し、公開鍵をファイルに保存します。
```sh
openssl rsa -pubout -in private_key.pem -out public_key.pem
```

以上で、2つのファイルが作成されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1328154/33402cf9-552f-c941-a8e7-41a442c898e9.png)

### データを暗号化する
`sample.txt`ファイルを作成し、公開鍵で暗号化を行います。そして、`.bin`ファイルでバイナリ形式のデータとして保存します。
```sh
echo "This is sample" > sample.txt

openssl pkeyutl -encrypt -in sample.txt -pubin -inkey public_key.pem -out encrypted_sample.bin
```

### データを複合する
秘密鍵を用いて、`encrypted_message.bin`ファイルを複合し、decrypted_sampleに保存します。
設定したpass phraseを入力します。
```sh
$ openssl pkeyutl -decrypt -inkey private_key.pem -in encrypted_sample.bin -out decrypted_sample.txt

Enter pass phrase for private_key.pem:
```

## 終わりに
公開鍵を用いて、暗号化し、秘密鍵を用いて複合する流れを実践しました。
どのように暗号化が行われているか流れがつかめました。
理解するには実際にやってみるのが近道ですね。
実効値を使う理由・電力計算で共役複素数に変える必要がある理由

# 実効値を使う理由
電力計算を成立させるために、実効値表示は存在します。

```math
P=V_a I_a
```

次のように置きます。

```math
\begin{eqnarray}
V_m,I_m:最大値\\
V_{ave},I_{ave}:平均値\\
V_a,I_a:実効値
\end{eqnarray}
```
次の表が求まります（積分計算の結果）

|電圧  |電流 |$V_m$に対する振幅比  | $I_m$に対する振幅比  | $V_mI_m$に対する比率  | 
|---|---|---|---|---|
|$V_m$   |$I_m$   |1  |1  | 1|
|$V_{ave}$   |$I_{ave}$   |$\frac{2}{\pi}$  |$\frac{2}{\pi}$  | $\frac{4}{\pi^2}$|
|$V_a$   |$I_a$   |$\frac{1}{\sqrt{2}}$  |$\frac{1}{\sqrt{2}}$  |$\frac{1}{2}$|

電力$P$を計算します。

```math
\begin{eqnarray}
P&=& \frac{1}{T}\int_0^{T}  V(t) I(t) dt\\
&=& \frac{1}{T}\int_0^{T} V_m \sin \omega t \times I_m \sin \omega t dt\\
&=& V_m I_m \frac{1}{2}\\
&=& V_a I_a
\end{eqnarray}
```

最後の2行が大切です。

**最大値同士で掛けると2倍になる**
**実効値同士で掛けると正常値になる**

実効値で電流・電圧表示しておくと電力計算がすぐできるのです！これが実効値表示を使う理由です！


# 共役複素数にする必要がある理由
フェザー表示を用いると、計算は楽になるがところどころ小骨が引っかかるような感覚があり、特に共役複素数に変換する点に関して違和感を感じる。


## 問題提起：抵抗の消費する電力

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/405484/ab3ea9b6-3094-f787-b831-a6fdbc59f5b2.png)


次のような回路の場合

```math
V= \sqrt{2} | \dot{E}| e^{j\omega t}
```
とすると

```math
i_R = V/R = \sqrt{2} \frac{| \dot{E}|}{R} e^{j\omega t}

```
となる（嘘）。

消費電力Pは

```math
P=V\times i_R = 2\frac{| \dot{E}|^2}{R} e^{2 j\omega t}
```
となる。ここでの消費電力は瞬時電力と呼ばれます。周期で積分して平均電力を求めましょう。

```math
P_{ave} = \frac{1}{T} \int_0^{T}  2\frac{| \dot{E}|^2}{R} e^{2 j\omega t} dt
```
しかし、複素関数の積分となってしまう。また、正しい電力は$\frac{E^2}{R}$である。

なぜうまくいかないのだろうか

結論から言えば、電力計算では片方を共役複素数にしないといけないのである。

```math
P=V\times i_R^*
```
## なぜ共役複素数にしないといけないのか

**計算の辻褄を合わせる結果**これが理由である。

そもそも、電圧に虚部は存在しない。存在しないものを追加し、実数の計算方法をそのまま拡張し、結果うまくいかなかっただけなのである。原理は存在しない。人間側の都合で追加したものの後始末をつけるだけである。
共役複素数を取って掛け算をするとちょうど人間が余分に追加したものが消えただけである。仮に複素共役を取ってうまく行かなかったら、別の方法が採用されていただろう。そうすると都合が良かったそれだけだ。
よって、実際に正しく計算できていることを確認・証明すれば、十分である。それ以上の追求に意味はない。


```math
\begin{eqnarray}
P &=& Re (\dot{E}\times \dot{I}^*)\\
&=&  Re( | \dot{E}| e^{j \omega t + j\theta_E}  | \dot{I}| e^{-j \omega t - j\theta_I} )\\
&=&  Re( | \dot{E}|  | \dot{I}| e^{ j(\theta_E - \theta_I)} )\\
&=&  | \dot{E}|  | \dot{I}| cos (\theta_E - \theta_I )
\end{eqnarray}
```

実部のみで計算した値と一致すれば、確認完了である！


# 実部のみで計算する

```math
E = \sqrt{2} | \dot{E}| sin(\omega t + \theta_E)
```
とすると

```math
I = \sqrt{2} | \dot{I}| sin(\omega t + \theta_I)
```
となる。
消費電力Pは

```math
P=E I= 2| \dot{E}|| \dot{I}|sin(\omega t + \theta_E)sin(\omega t + \theta_I)
```
となる。ここでの消費電力は瞬時電力と呼ばれる。周期で積分して平均電力を求める

```math
\begin{eqnarray}
P_{ave} &=&\frac{1}{T} \int_0^{T}  2| \dot{E}|| \dot{I}|sin(\omega t + \theta_E)sin(\omega t + \theta_I) dt\\
&=&\frac{1}{T} \int_0^{T}  2| \dot{E}|| \dot{I}|\frac{1}{2} [cos(2 \omega t + \theta_E +\theta_I) - cos (\theta_e - \theta_I) ] dt (和積の公式を使用)\\
&=&\frac{1}{T}  2| \dot{E}|| \dot{I}|  cos (\theta_e - \theta_I) \frac{1}{2} T\\
&=& | \dot{E}|| \dot{I}|  cos (\theta_e - \theta_I)
\end{eqnarray}
```
と計算できる。

正しく計算できた。確認完了！！！


# 補足：無効電力の正負

遅れ無効電力を正（＋）とする。

理由はない。

個人的にコイルでは電流は電圧基準で負の方向を向いているため。無効電力は負になる気がするが、逆になる。
だからこそ

```math
P = \bar{E} I 
```

ではなく

```math
P = E \bar{I}
```
となるのだろう.

覚え方：愛には裏がある

（追加）最近読んだ本では正負逆で設定しているものがあった。あくまで定義の話になるので、統一されていればどちらでも本質的には問題ない。注意が必要だ。
電気回路の解析における簡約化補助

# はじめに
前提として、キルヒホッフの法則とオームの法則と重ね合わせの理を理解していて、立式まではできるものとします。
また本記事の内容はきちんと精査していないので、正しく動いてくれれば良いなと祈っている状態です。
自分が線形代数をまったく真面目に勉強していなかったので、連立一次方程式で過剰な式を与えた時にうまく回答を出す方法が分からなかったため、最初から正則な立式を目指しました（電源をパラメータにしたら当然正則ではなくなりますが）。
過剰に式を与えても簡単に連立一次方程式を上手く解く方法があれば、この記事はゴミになります。

# 対象読者
* 試験などで手計算する際にえいやで未知数分立式し、とりあえず変形して`0 = 0`にならない事を祈っている人
* プログラムで電気回路の解析を自動計算しようとしていて、正則な行列を電気回路的なアプローチで作りたい人

# 手順
1. 電源を1つ選び（電源A）、その電源を通る回路を1つ取り出す
1. 手順1で取り出した回路上にある負荷が形成する（電源を含まない）回路を全て取り出す
    * 電源を含んでいても問題ないが回路の探索は指数関数的に増えるはずなので、許されるなら除外したい
    * 電源を含まない事で、媒介変数部や右辺を必ず0で立式できるので考えることが減って楽
1. これまでの手順で取り出した回路の中で短絡された箇所をグルーピングし、各グループに対して電流のキルヒホッフ式を立てる
    * 他の電圧源がある場合も短絡として扱う
    * 自分は、「スイッチの前後で分割された静的な同電位」、「スイッチ状態を反映した動的な同電位」、「他の電圧源を短絡とみなした仮想同電位」の3段階で電位グループを管理していました
1. 手順2で取り出した回路の中から不要回路の除外を、回路数が（回路上の全負荷数） - （手順3の式数） - 1になるまで実行
    * 不要な回路：その回路を除外しても含まれる負荷数が減らない回路
1. 手順4で残った回路に対して電圧のキルヒホッフ式を立てる
1. 電源Aの種別によって最後のキルヒホッフ式を立てる
    * 電圧源の場合
        * 手順1の回路で電圧のキルヒホッフ式を立てる
    * 電流源の場合
        * 電流源の一方で電流のキルヒホッフ式を立てる
1. 別の電源があれば手順1に戻り別の電源を選ぶ
1. たぶんいけます

# さいごに
コーディングは祈り。
これはおかしいとかありましたら、反例か証明をお願いします。自分自身ふわっと実装してるので軽く説明されてもわかりません。
AnsibleでLinuxのIPv6を無効化する【初心者】

# はじめに
IT初心者の雑記です。
間違いを見つけたら指摘していただけると泣いて喜びます。

# 検証環境
仮想化基盤: Virtualbox7
ゲストOS  : CentOS Stream 9
Ansible core version: ansible [core 2.15.12]

# 結論
カーネルのパラメータをいじるsysctlを扱えるモジュールであるansible.posix.sysctlでipv6を無効化するパラメータを入れれば終わり。
具体的に書くと
``` main.yml
- name: disable ipv6
  ansible.posix.sysctl:
    name: "{{ item }}"
    value: "1"
    state: true
    reload: true
  with_items:
    - net.ipv6.conf.all.disable_ipv6
    - net.ipv6.conf.default.disable_ipv6
```
こうなる。
指定した値をファイルに存在する状態とするstate: trueと、設定を反映させるreload: trueはどちらもデフォルトでtrueなので指定しなくとも良いが、分かりやすさ重視で書いた。

## やってること
上記の動作で具体的にどこに作用しているのか。
```/etc/sysctl.conf```
このファイルにパラメータを書き込んでいるだけ。

## 手動なら
```/etc/sysctl.conf```に以下のものを書き込む。
```
net.ipv6.conf.all.disable_ipv6 = 1
net.ipv6.conf.default.disable_ipv6 = 1
``` 
上記のファイルを反映させるために次のコマンドを実行。
~~~bash
sysctl -p
~~~

以上

### 参考さまさま
https://docs.ansible.com/ansible/latest/collections/ansible/posix/sysctl_module.html

https://qiita.com/dan-go/items/f040f838907e2ab5b510
強連結成分分解アルゴリズムの正しさの証明

グラフ理論において**強連結成分分解**とは, 有向グラフの頂点を以下の条件を満たすようにグループ分けすることです。
$$
任意の2頂点A, Bについて, AとBが同じグループに属する
$$
$$
\iff 有向グラフ上でAからBへの経路, BからAへの経路がともに存在する
$$  
自分は競技プログラミングをしていてこの概念を知りました。  
このようなグループ分けは, 以下のようなアルゴリズムで達成できることが知られています。

1. グラフ上の頂点を1つ選び, そこから到達できる点を深さ優先探索で探索する。
2. 探索の帰り際に1から順に頂点に番号をつける。これが終わったらまだ探索されていない点を1つ選び, 同様に深さ優先探索で番号をつけることを, 全ての頂点に番号がつけられるまで繰り返す。一度探索した点は2度以上探索しない。
4. グラフの全ての辺を逆向きにし, 2・3でつけた番号の大きい点から順に探索する。一度の探索で訪問した点を同じグループとしてまとめる。

このアルゴリズムが正しいことの証明を調べたのですが見つからなかったので, 自分が考えた証明を書こうと思います(間違っていたら指摘していただけるとありがたいです)。

　　1. 用語の定義
証明にあたって, 以下の用語を定める。
- 点$X$から$Y$への経路を$\overrightarrow{XY}$と書き, $\overrightarrow{XY}$が存在することを$E(\overrightarrow{XY})$とかく。また$E(\overrightarrow{XX})$が常に成り立つとする。
- 2回の探索のうち1回目の探索を**探索1**, ｓ2回目の探索を**探索2**とする。
- 頂点$X$につけられた番号を$p(X)$とする。
- 探索2において, $X$が点$Y$から出発した探索時に訪問されたとき, $g(X)=Y$とする。  

2点$A, B$が同じグループにあることは, $g(A)=g(B)$と同値となる。  
また定義より, 
$$
g(X)=\mathrm{argmax}_{Y: E(\overrightarrow{XY})}p(Y)
$$
である。  
$E(\overrightarrow{XX})$であるから, $p(g(X))\ge  p(X)$となる。

任意の2点$A, B$に対して
$$
g(A)=g(B)\iff E(\overrightarrow{AB})かつE(\overrightarrow{BA})
$$
であることを示せばよい。


　　2. $E(\overrightarrow{AB})$かつ$E(\overrightarrow{BA})\implies g(A)=g(B)$の証明
探索2において, 一般性を失わずに$B$より先に$A$を訪問したとしてよい。　　

$A$訪問時, 探索2の深さ優先探索のスタックに, $\overrightarrow{BA}$の経路上の点がなければ, $A$からの探索において$B$が訪問されるので, $g(A)=g(B)$となる。

$A$訪問時, 探索2の深さ優先探索のスタックに, $\overrightarrow{BA}$の経路上の点が含まれる場合, その中で最も$B$に近い点を$C$とすると, $E(\overrightarrow{BC})$なので, $C$からの探索で$B$が探索される。よって, やはり$g(A)=g(B)$となる。

　　3. $g(A)=g(B)\implies E(\overrightarrow{AB})$かつ$E(\overrightarrow{BA})$ の証明
$g(A)=g(B)=X$とおく。まず$E(\overrightarrow{AX})$かつ$E(\overrightarrow{XA})$であることを示す。  
$X=A$のときは自明なので, $X\ne A$とする。
定義より, $E(\overrightarrow{AX}), p(A)<p(X)$ である。  
探索1において, $X$より先に$A$に訪問したとする。  
$E(\overrightarrow{AX})$より, $p(X)>p(A)$となるためには, $A$訪問時の深さ優先探索のスタックに$E(\overrightarrow{AX})$の経路上の点が含まれているはずである。その点の中で最も$X$に近い点を$C$とすると,$E({\overrightarrow{AC}})$かつ $E(\overrightarrow{CX})$となり, $\overrightarrow{CX}$上にスタック上の点は存在しないので, $p(X)< p(C)$となる。しかしこのとき$g(A)=C$となり矛盾する。  
よって$X$の方が$A$より先に訪問されている。  

このとき, $p(A)< p(X)$となるためには, $X$到達後, その下流の探索で$A$に到達する必要があり, $E(\overrightarrow{XA})$であることがわかる。よって$E(\overrightarrow{AX})$かつ$E(\overrightarrow{XA})$が示された。

同様に, $B$についても$E(\overrightarrow{BX})$かつ$E(\overrightarrow{XB})$である。   
よって, $A\to X\to B, B\to  X\to A$という経路が存在するから, $E(\overrightarrow{AB})$かつ$E(\overrightarrow{BA})$である。
【IVS探訪記】AI/データエンジニアがIVSに行ってきました!

# IVSに行ってきました！
初めまして！[株式会社 Panta Rhei](https://www.pantarhei.co.jp/)でデータ周りをいじったりCEOをやってたりする者です。
今回は国内最大級のスタートアップカンファレンスであるIVSに行ってきました！

# IVSとは?

https://www.ivs.events/ja

IVS2024で31回目を迎える、老舗なスタートアップ向けのイベントです！
参加人数は1万人以上！セッション数も250を超えるなど、非常に大規模なイベントです。

# IVSに行った感想

<B>1. 世界観がめっちゃ70s~80s</B>
<B>2. 学生が非常に多い！</B>
<B>3. AI/データエンジニアとして楽しめるか</B>

## 1. 世界観がめっちゃ70s~80s

まずこちらをご覧ください。

https://www.youtube.com/watch?v=QddtXFLLUmk

公式テーマソングだそうですが、めちゃくちゃディスコミュージック味あります。
Winkっぽい感じもします。
会場も全体的にEarth, Wind & Fire感がすごかったです。

下の画像はスタートアップのHR系のエリアの画像広告ですが、

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/540865/8714499b-76a6-83e6-a9f7-170884b0b837.png)
出典: IVS公式(https://www.ivs.events/ja)

沢田研二と尾崎豊のハイブリッドな感じの男性と、聖子ちゃんカットの女性が写っております。

個人的に私はこの時代が非常に好きなので(生まれてないですが)、雰囲気はめちゃくちゃ楽しかったです！

## 2. 学生が非常に多い！

今回、学生向けチケットを<B>5,000円</B>という破格の価格(Business PassのStartup向けチケットは83,000円)で提供したこともあってか、非常に学生が多かったです。
本当に学生が多かった。体感3~4割は学生だったのでは?といった感じでした。
起業を目指す学生がこんなにもいるんだと驚きましましたし、私も経営者として刺激を受けました。
この情報化社会だともう年齢差≠実力差なわけですが、やっぱり自分より若い方々には負けたくないです。
頑張りましょう、となりました！

## 3. AI/データエンジニアとして楽しめるか
本題です。私の結論は2つあります。

<B>1. 異なるカルチャーを楽しむなら最高</B>
<B>2. 技術イベント行くノリで行くと最大限楽しめないかも</B>

といった感じです。
楽しむためには、サイドイベントなどに積極的に顔を出す、ブラブラしている人に話しかける、などのアクションが必要で、いわゆるコミュ力が求められました。
びっくりしたのは、館内で一人でコーヒーを飲んでたところ「ちょっとお話しいいですか！」と話しかけられたことです。
実質ナンパでした。結構気圧されながらも話してみるとめちゃくちゃ楽しい。
ギークな世界では絶対に知り得ない雰囲気や会話を楽しめました！

一方で、技術イベントいくノリで行くと、フルに楽しむのにストッパーがかかってしまうのかなと思いました。技術系イベントは同質のメンバーが集まりやすい。したがって会話する時も勇気などはあんまり必要がないし、言葉遣いへの配慮や既知単語がある程度共通で会話に気を払いすぎない、といった部分があると思います。

IVSはかなりイケイケ寄り(そこから分岐して「イケイケかつ〇〇」)な方々が多く、AI/データエンジニアとは普段交流のない陽なカルチャーがありました。普段以上にコミュ力と積極性と勇気を持たないと、交流が発生しにくく楽しみにくいのかなぁと感じました。

<B>コミュ力を鍛えましょう！(自戒)</B>

# まとめ
<B>勇気を持って話してみよう！さすれば道は開かれる！</B>
というイベントでした。肝に銘じたいと思います。

# 簡単な自己紹介
スタートアップといえば[株式会社 Panta Rhei](https://www.pantarhei.co.jp)ですね。
AIの活用やAIの能力をフルに引き出すデータ基盤。
KagglerもGoogle Cloud認定資格者もいるギークだけど元気なスタートアップです。
ぜひご興味ある方はホームページからご一報ください！
投稿 13 クロック 2024/07/13

本日の勉強時間　3H


クロックは，一定の間隔でパルスの“1”と“0”を繰り返す信号

CPIは命令１つに対しての平均クロック数。
CPUクロック周期はクロックが発生する間隔。
1命令処理に要する時間は
CPUクロック周期×CPI。
簡単、便利、手間要らずでPythonからPDFが読み込める！？pypdfを使ってみた

# 概要
最新のAI技術の動向をキャッチアップするためには英語論文から情報を得ることは避けて通れません。しかし、英語で数10ページの文章を読むのはいささか骨が折れます。AbstractとConclusionだけなら何とか英語のまま読むとして、本文を全部は読まないにしてもIntroducitonやRelated Work、Discussionなどを全部英語で読み通し、なおかつ数も熟す。。。今の筆者には到底不可能な離れ業です。そこで、徐々にそうなるために訓練をするとして、まずは英語論文を継続的に読む習慣をつけることにしました。昨今はGoogle翻訳やDeepL翻訳など機械翻訳アプリケーションの性能も一昔前とは比べ物になりません。しかも、DeepL翻訳はAPIが公開されており、一部文字数などに制限が有りますが、無料で利用出来ます。論文PDFを渡してスクリプトを実行したら翻訳付きPDFが出力されるツールを作るのも一興と思い、その前準備としてPythonからPDFを読み込むためのライブラリpypdfを使ってみることにしました。

# 環境構築
今回は以下の環境を用いました。

* macOS Sonoma 14.5
* Python 3.10.7
* notebook(旧Jupyter Notebook) 7.2.1
* pypdf 4.2.0

# 実際にPDFを読み込んでみる
Notebook上でpypdfを実行してPDFを読み込んでみることにします。事前に読み込むPDFファイルを用意しておきます。筆者は以下の英語論文を読み込んでみることにしました。

https://arxiv.org/pdf/2405.21060

公式ドキュメントの以下のページを参考にPDFを読み込んでみます。

https://pypdf.readthedocs.io/en/stable/user/extract-text.html

以下のコードをNotebook上で実行しました。全ページのテキストを抽出すると途轍もない分量になるので1ページのみ抽出します。

```python:コード例
from pypdf import PdfReader

reader = PdfReader("pdf/Transformers_are_SSMs.pdf")
pages = reader.pages

# 全ページのテキストを抽出する場合、以下のfor文を実行
# for i, page in enumerate(pages):
#     print(f"Page {i+1}")
#     print(page.extract_text())
print(pages[0].extract_text())
```

正しく1ページ目のテキストが抽出されています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/fce11213-5c3b-24f4-2ded-80444dcbf840.png)

続けて、レイアウトモードでテキストを抽出してみます。extract_text()ファンクションに引数extraction_mode="layout"を与えるだけです。

```python:レイアウトモードで抽出
print(pages[0].extract_text(extraction_mode="layout"))
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/ec3ec88f-1494-e85e-5fb0-d1190b30229e.png)

縦方向の余分な空白を削除して表示してみます。

```python:縦方向の余分な空白を削除
print(pages[0].extract_text(extraction_mode="layout", layout_mode_space_vertically=False))
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/f3ee4de4-0ccb-8e3c-1b20-59b939a9e7b2.png)

最終的にDeepL翻訳に投げることを考えると、レイアウトモードでの抽出は適さないと考えました。(因みに、レイアウトモードでの`Rotated text discovered. Output will be incomplete.`という警告は、論文の左端に回転文字の透かしが入っているのが抽出出来なかったことから出ている様です。)ここで、縦方向の余分な空白のみ削除して抽出してみることにしました。

```python
print(pages[0].extract_text(layout_mode_space_vertically=False))
```

これでテキストの抽出及び余分な空白の削除に成功しました。最終行の`1arXiv:...`の部分が回転文字透かしの部分です。これは不要なので最終的には取り除きたいですが、今回のテストではそのままにしておきます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/ac7b99e7-68b2-6fc5-b5bd-972dd81861df.png)

# まとめ
無事に英語論文PDFからテキストの抽出に成功しました。抽出したテキストからDeepL翻訳に投げるべきテキストの選択は正規表現などを用いることで指定出来るだろうと考えています。今回は検証しませんでしが、追加の機能をpypdfにインストールすることで、図の抽出なども出来る様になります。

# Reference
https://pypdf.readthedocs.io/en/stable/index.html
CUDAのお勉強と自分用メモ

CUDAを勉強したくなったため勉強します。
もしも間違えているところがあれば教えてくださるとうれしいです。

# 教材
2012/03/18で少し古いけどYoutubeにあったCUDA プログラミング入門

https://www.youtube.com/watch?v=dnuACytuVsU

NVIDIAのCUDAプログラミングの基本

https://http.download.nvidia.com/developer/cuda/jp/CUDA_Programming_Basics_PartI_jp.pdf


# CPUとGPUの違いはこんな感じ

|項目| CPU |GPU |
|:-:|:-:|:-:|
|コア数はどのくらい？|少量|大量|
|どんな処理|   複雑|  単純 |
|どっちがメイン？|メイン|サブ|


# GPUの中はどうなっているか

GRID
　Block
　　Thread
　　Thread
　　...
　Block
　　Thread
　　Thread
　　...
　...
 のような階層構造を取っている
 ## GRIDやBlock、Threadは何？
 Blockの中のThreadで同期をとる
 Block間は別の処理を行える

# プログラムの流れ
```mermaid
graph TB;
    プログラムで並列計算が必要-->GPUのメモリを確保(元データ用と計算結果用);
    GPUのメモリを確保-->計算に必要なデータを用意したメモリに送る;
    計算に必要なデータを用意したメモリに送る-->データをもとにGPUで計算;
    データをもとにGPUで計算-->GPUで計算したデータをCPUに送る;
    GPUで計算したデータをCPUに送る-->確保していたGPUメモリを破棄;
```

# CUDAAPIについて
cudaを動かすためにはC/C++に似た言語を使用する。違いはCUDAAPIがあることだ。
## GPUのメモリ確保と破棄
```cuda
cudaMalloc(void** pointer, size_t nbytes)
cudaMemset(void** pointer, int value, size_t count)
cudaFree(void** pointer)
```

C/C++に慣れていない人用
C/C++にはメモリの場所を使って、プログラミングすることがある。
場所を設定するときに使用するのがポインタというもの。配列もこれを使用する。配列の場所を色々したいからポインタのポインタというものが存在する。今回はこれ。だと思う...

# 箸休め
2024/07/20~2024/07/28までコロナになった。辛い、これを読んでくれた人はコロナらないように健康に気を付けて...

# 勉強中
勉強したら再度編集するつもりです。
iOS のバージョン・プラットフォームで処理を分ける方法

たまーに、使う。そのたまーに使うから思い出せない。
ので、メモ書きです。

# バージョンでの処理について
プラットフォームやバージョンごとに利用可能・不可能なコードの断片を書くことは、変化し続けるアプリ開発の状況で必要だと考えます。
個人的な意見、バージョンごとにコードの断片を書くことは Issue に書くより、コードに書く方が良いと考えています。
理由として、Issue に書いてしまうと他の Issue に埋もれて隠れてしまい、忘れ去られてしまうからです。TODOリストなどでも、いつまで経っても処理されないタスクってありますよね。
この問題を解決するためにも、新しいAPIを使って実装し、バージョンごとに分割する手法を取ると良いかなぁと考えます。

この記事では、バージョンごとに処理を分ける方法について解説します。

# OSのバージョンで処理を分ける
iOS開発において、よく目にする処理だと思います。`#available` を使うとOSのバージョンごとにコードを分けることができます。

```swift:if 文の場合
if #available(iOS 15.0, *) {
    /// iOS 15.0以降の時はここを通る
} else {
    /// iOS 15.0より前の時はここを通る
}
```

```swift:guard文の場合
guard #available(iOS 15.0, *) else {
    /// iOS 15.0より前の時はここを通る
}
/// iOS 15.0以降の時はここを通る
```

# `@available` と `#available` の違い
Swift API には、`available` と調べると、@ があるものと、# があるものの、2通りがあります。それぞれ何が違うのでしょうか。
公式ドキュメントでは以下のように説明されています。
- `@available`: 特定のターゲットプラットフォームのアプリを構築する際に宣言を使用するかどうかを制御する
- `#available`: 必要なプラットフォームとバージョン状況に基づいて条件付きでコードを実行します

# `@available`
`@available` を使うことで、利用可能なクラスまたはメソッドを制御することができます。
例えば、iOS14よりも低いバージョンでサポートするプロジェクト内に以下のクラスのインスタンスを作成するとエラーが発生します。

```swift
@available(iOS 14, *)
final class NewAppIntroduction {
    // 任意のインスタンス
}
```

このコードは、`#available` を使って以下のように実装すると使えるようになります。

```swift
if #available(iOS 14, *) {
    let appIntroduction = NewAppIntroduction()
} else {
    // iOS14 より前の処理
}
```
また、`@available` を使って同様な処理を作成しても作ることができます。

```swift
@available(iOS 14, *)
func launchNewAppIntroduction() {
    let appIntroduction = NewAppIntroduction()
}
```

# 非推奨または廃止をマークする
`@available` は非推奨・廃止としてマークすることもできます。
以下のコードは、iOS12より高いバージョンでは非推奨とし、iOS13より高いバージョンでは廃止としてアラートが表示されます。
```swift
@available(iOS, deprecated: 12, obsoleted: 13, message: "We no longer show an app introduction on iOS 14 and up")
func launchAppIntroduction() {
    // ..
}
```

# メソッド名の変更をマークする
OSSやSDK、Packageを作成している人は、実装者へ向けてコードを新しいAPIを使用させたい場合に以下のように実装すると良いでしょう。

```swift
@available(*, unavailable, renamed: "launchOnboarding")
func launchAppIntroduction() {
    // 古い処理
}

func launchOnboarding() {
    // 新しい処理
}
```
廃止としてマークしていることに注意してください。renamed では、代わりにどのAPIを使えば良いかを示します。

# プラットフォームで処理を分ける
iOS と MacOS で処理を分けたい場合は、以下のように行います。

```swift: iOS のみ処理を分ける
#if os(iOS)
// iOS に関する処理
# else 
// その他プラットフォームに関する処理
# endif
```

また、SimulatorやMac Catalystなど、特定の環境向けにコンパイルしたり、コンパイルしないようにしたりすることもできます。

```swift: シュミレータのみ処理を分ける
#if targetEnvironment(simulator)
    // シュミレーターに関する処理
#endif
```


# 参考文献

https://www.avanderlee.com/swift/available-deprecated-renamed/

https://zenn.dev/youandtaichi/articles/42c2677af0336d

https://developer.apple.com/documentation/xcode/running-code-on-a-specific-version