OmniAICreator/Qiita-1.07M huggingface dataset:
画像を縮小する【道具としての OpenCV 画像認識】

# 本記事でできること
画像を読み込んで、縮小して表示します。
![shrink_image_3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/37698/ee5c1dba-ec2d-8342-745c-0c25d4529955.png)


# 想定シーン
## ロボットをビジュアルフィードバック制御する
カメラを使ったロボットアームの制御方法を、ビジュアルフィードバック制御といいます。ここでは、ビジュアルフィードバック制御を使った自動化システムを開発する際に必要となる画像認識プログラムをまとめています。

## 画像を縮小する
工業用カメラの画素数は640×480ピクセルの小さなものから、1920×1080ピクセルの大きなものまで、さまざまな機種がラインナップされています。ただ、画像検査等ではなく、ロボットのビジュアルフィードバック制御でカメラ画像を使用する場合にはあまり高い解像度でないほうが、処理時間を短縮できて便利です。ここでは、取得した画像を縮小するプログラムを掲載します。


# 実行環境
- OS：Ubuntu 22.04 LTS
- 言語：C++
- クルーボ：v5.1.0

## クルーボについて
ロボットアプリケーション開発には、株式会社チトセロボティクスのロボット制御ソフトウェア「クルーボ」を使用します。本記事のプログラムは、クルーボがインストールされた制御コンピュータ上で動作します。

- クルーボの製品サイト：https://chitose-robotics.com/product

## プログラム抜粋
```C++
cv::Mat shrink_image(const cv::Mat& image, const cv::Size resized_size) {
    cv::Mat resized_image;
    float resized_width = (float)resized_size.width;
    float resized_height = (float)resized_size.height;
    float image_rows = (float)image.rows;
    float image_cols = (float)image.cols;
    float resized_ratio = std::fmin(resized_width / image_cols, resized_height / image_rows);

    if (resized_ratio < 1.0) {
        cv::resize(image, resized_image, cv::Size(), resized_ratio, resized_ratio, cv::INTER_NEAREST);
    } else {
        resized_image = image.clone();
    }
    return resized_image;
}
```

## 全体プログラム
```c++
#include <iostream>
#include <opencv2/opencv.hpp>

cv::Mat load_image(const std::string file_path) {
    cv::Mat loaded_image = cv::imread(file_path, 1);
    if (loaded_image.empty()) {
        throw std::runtime_error("画像を正常に読み込めませんでした。");
    }
    return loaded_image;
}

cv::Mat shrink_image(const cv::Mat& image, const cv::Size resized_size) {
    cv::Mat resized_image;
    float resized_width = (float)resized_size.width;
    float resized_height = (float)resized_size.height;
    float image_rows = (float)image.rows;
    float image_cols = (float)image.cols;
    float resized_ratio = std::fmin(resized_width / image_cols, resized_height / image_rows);

    if (resized_ratio < 1.0) {
        cv::resize(image, resized_image, cv::Size(), resized_ratio, resized_ratio, cv::INTER_NEAREST);
    } else {
        resized_image = image.clone();
    }
    return resized_image;
}

int main(void) {
    std::string file_path = "../data/fuji.jpg";
    const cv::Mat loaded_image = load_image(file_path);

    const cv::Size resized_size(320, 240);
    const cv::Mat shrinked_image = shrink_image(loaded_image, resized_size);

    cv::imshow("loaded_image", loaded_image);
    cv::imshow("shrinked_image", shrinked_image);
    cv::waitKey(0);
}

```

## おわりに
人手作業をロボットアームで自動化するために、カメラを使ったロボット制御＝ビジュアルフィードバック制御が大切です。
ロボット制御用の画像認識でも中身のひとつひとつはシンプルなので、要素に分解して解説していきたいと思います。
CopilotでPowerAppsアプリ作ってみたpart1

※今回は知識もなく特攻するスタイルで作っていきますので手順とかではないです
というか手順がいらないからAIだよね（？）


## 準備
・PowerPlatformの環境を準備します
・環境を作るときに地域を「米国」に設定して環境を作ります

## カスタマイズ画面にCopilot登場！
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/b4d85826-9e7c-879d-6aeb-aa7d4ef2666f.png)


これはちょっと感動
ワクワクします

## いざ「Copilotで開始する」をクリック

...ん？
あ、右下に何か文字を入れる感じね

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/b76f2e0a-1cf3-288e-f8b6-ad5e27f1db47.png)

左下にはサンプルがあるけど
これは結構やってる人じゃないとわからない言葉がいくつかありますね

## 話かけてみる
「勤怠管理アプリ」を作ってみようと思います
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/e2bb50b9-4a9e-e669-a98f-bf6732e8c21f.png)

何やらエラーがありますね
まだ右下の「アプリを作成する」が押せないみたいです

## さらに追加要望
どちらかというと管理者の画面を作ってくれたので、もう少し社員よりの画面が欲しいですね。
とのことで追加要望

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/e8d60406-f089-9bee-0c60-f69a370c0965.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/693adf77-567c-1719-cee4-4c6514522023.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/6f967683-1bea-830b-a636-f0f292a62fc5.png)


やや雲行きが怪しくなってきました

最初からやり直すには右上の更新マークを押します
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/25b9b599-23ff-ffca-326f-79c288e6a3af.png)

## 再チャレンジ

キャンバスアプリを作ってほしいので日本語をもう少し丁寧に
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/816218b5-c38c-7d27-32c6-9f876803079b.png)

どうしてもモデル駆動型アプリで作ってくれるようです。
ただ今回は右下の「アプリを作成する」ボタンが押せるようになりました

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/9dd6cfe9-b421-a45f-fcfd-00ef944ddbd3.png)




## 最終手段「ちょっと詳しい言葉でお願いしてみる」
「キャンバスアプリで作って！」

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/bfe43cca-601c-0788-de30-0a2f2871f6ab.png)


ん～惨敗といったところでしょうか

## 作れない原因
考えられる原因はいくつかあります
・指示文が少ない
・具体的な指示が少ない
・日本語版がリリースされたばかりで性能が追い付いていない


## 次への課題
ひとまずモデル駆動型アプリは作れることが分かったので次回は作ってみようと思います。

またキャンバスアプリをどうしても作りたいニキなので、今度は英文でもお願いしてみようかなと


前知識なく特攻してみた結果でした。
画面に文字列を表示

# 関連記事

https://qiita.com/yokan/items/38355a806fb4df7129cc

# 開発環境
- Windows11
- Visual Studio 2022

# printf関数
`printf`（プリントエフ）関数は書式文字列の内容を画面に表示する関数です。まずは簡単な使い方から紹介します。

```c
#include <stdio.h>

int main( void )
{
    printf( "Hello" );
    return 0;
}
```
```txt:実行結果
Hello
```
printf関数には画面に表示したい文字列を実引数として渡します。この文字列は、必ずダブルクォート`"`で囲んでください。

画面に表示させる文字列として全角文字の使用も可能です。数字や記号も使えますが、\\は特殊な記号なのでそのままでは使用できません。これは後ほど解説します。

```c
#include <stdio.h>

int main( void )
{
    printf( "こんにちは！Hello!!12345" );
    return 0;
}
```
```txt:実行結果
こんにちは！Hello!!12345
```

# 改行
printf関数はプログラム中に何度も呼び出すことができます。ただし、改行は行われません。
```c
#include <stdio.h>

int main( void )
{
    printf( "Hello" );
    printf( "こんにちは" );
    return 0;
}
```
```txt:実行結果
Helloこんにちは
```

改行を行うには **エスケープシーケンス(拡張表記)** を使います。

## エスケープシーケンス
エスケープシーケンスとは特別な動きをする文字のことで、`\`記号と1文字の組み合わせで表現します。

:::note
環境によってはバックスラッシュが半角の円記号（￥）として表示される場合がありますが、機能的には同じです。
:::

例えば改行を表す拡張表記は`\n`です。これをprintf関数の文字列中に記述すると改行が行われます。
```c
#include <stdio.h>

int main( void )
{
    // Hello の後に改行されて こんにちは と表示される
    printf( "Hello\nこんにちは" );
    return 0;
}
```
```txt:実行結果
Hello
こんにちは
```
また、拡張表記は文字列中に何度でも使用することができます。

```c
#include <stdio.h>

int main( void )
{
    printf( "こ\nん\nに\nち\nは" );
    return 0;
}
```
```txt:実行結果
こ
ん
に
ち
は
```

## \\の表示
バックスラッシュ`\`は、エスケープシーケンスに使われる特殊な記号であるため、そのままプログラムに記述しても文字として画面に表示されません。バックスラッシュを文字として表示するには、`\\`というエスケープシーケンスを使う必要があります。

```c
#include <stdio.h>

int main( void )
{
    printf( "バックスラッシュの記号は\\です。" );
    return 0;
}
```
```txt:実行結果
バックスラッシュの記号は\です。
```

# 書式化
printf関数に渡す文字列は書いた通りに表示されます。そのため、計算式などを書いても計算は行われずそのまま表示されます。
```c
#include <stdio.h>

int main( void )
{
    printf( "123と456の和は123 + 456です。" );
    return 0;
}
```
```txt:実行結果
123と456の和は123 + 456です。
```
プログラミングでは単に文字列を表示するだけでなく、計算結果を表示することが多々あります。これを実現するのが **書式指定子（フォーマット指定子）** で、文字列中に%と１文字の組み合わせで表現します。例えば%dは10進数の整数値で表示するという意味になります。

```c
#include <stdio.h>

int main( void )
{
    printf( "123と456の和は%dです。", 123 + 456 );
    return 0;
}
```
```txt:実行結果
123と456の和は579です。
```
書式指定子を使うときはprintf関数の2つ目以降の実引数に表示したい値を指定してください。値は数値だけでなく計算式を書くこともできます。
２つ目以降の実引数に計算式を書けば、その計算結果が%dのところに表示されます。

![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3713748/73295487-51ed-dd3b-6fc1-1b949729005d.png)

書式指定子は文字列中に何度も使うことができます。書式指定子の数だけ実引数を追加してください。

```c
#include <stdio.h>

int main( void )
{
    printf( "%dと%dの和は%dです。", 123, 456, 123 + 456 );
    return 0;
}
```

![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3713748/15c4b522-a453-8ac9-05bb-4f01fb095c22.png)
DBを正規化するということ

# はじめに
[楽々ERDレッスン](https://www.shoeisha.co.jp/book/detail/9784798110660)を読んだので、重要だと思った点についてまとめ。  
- One Fact in One Place
- ビジネスの視点から正規化

# One Fact in One Placeについて
データベース設計の基本的な考え方がOne Fact in One Placeである。  
日本語では「1つの事実が1つの場所にのみ存在する」ということ。  
これを実現するための一つの手法として、データベースの正規化が挙げられる。  
正規化というと、1つの事実を2つ以上の場所に置かない[^1]ことを想像してしまいがちである。  
しかし、2つ以上の事実を1つの場所に置かないことも重要だ。  

## 2つ以上の事実を1つの場所に置いた状態
具体例を交えて考えてみる。  
社員というテーブルを例に考える。  
![only_employee.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2529362/d641f504-f4de-95c5-813b-07b60fa78981.png)

上記のテーブルでは、退職区分というカラムがあり、現役の社員なのか退職済みの社員なのかという情報を持っている。  
現役社員の場合は、退職日がnullとなる。
退職済みの社員の場合は、セキュリティの観点から名前を保持しないため姓名がnullとなり、退職日に値が入る。  
社員という一つのくくりで表現しようとしているが、社員には現役と退職済みという2つの種類があり、2つの事実を1つのテーブルの中に持ってしまっている。  
区分というカラムによって、レコードの意味が変わってしまうという問題が発生している。  
解決するためには、One Fact in One Placeを進めていけば良い。  
![employee copy.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2529362/3c2d5ce8-663c-e3b9-a7b7-812899d3a166.png)


このようにすれば、現役社員と退職済社員の2つを別のテーブルで管理することができる。  
しかし、これだけでは十分ではない。退職済社員に着目すると、退職済社員というリソースの情報と、退職をするというイベントの情報が1つのテーブルにまとまっている。  
これらを分解すると、
![employee.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2529362/53909d3f-f21e-b64c-1564-f9edcf3c03e2.png)

のようになる。


# ビジネスの視点から正規化する
テーブルをわけて重複を排除していくことが正規化ではない。  
正規化とは、ビジネスの視点から情報を整理していくことである。  
例として商品の売上を管理するということを考える。  
![売上.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2529362/4b499e9d-8298-30e8-fb22-d66d8650783e.png)


前提として今回の説明と関係ない項目は極力排除してある。  
商品テーブルに単価を持たせているため、売上明細テーブルには商品の金額を持たせていない。  
また、商品テーブルの単価と売上明細テーブルの数量を見れば合計金額は導出できるため、売上テーブルに合計金額は持たせていない。  
テーブルの正規化というと上記のように、「持たせなくていいものをできるだけ持たせない」ということを想像してしまいがちである。  
しかし、これが常に正しいとは限らない。  
例えば、「今回のみ、この商品に関しては割引をして売る」ということが発生する場合、上記のテーブルでは表現することができない。この場合は、売上明細テーブルに販売価格を持つことが正しい。  
あるいは「全体の売上金額から端数を割引する」ということが発生する場合、売上テーブルに割引後の合計金額を持つことが正しい。  
このように、ビジネスで起こり得ることも加味したうえでテーブル設計を行う必要があり、ただ、テーブルをわけて重複を排除するのみが正規化ではない。

# 参考
- [楽々ERDレッスン](https://www.shoeisha.co.jp/book/detail/9784798110660)
- [イミュータブルデータモデル](https://scrapbox.io/kawasima/%E3%82%A4%E3%83%9F%E3%83%A5%E3%83%BC%E3%82%BF%E3%83%96%E3%83%AB%E3%83%87%E3%83%BC%E3%82%BF%E3%83%A2%E3%83%87%E3%83%AB)


[^1]: 例えば商品の売上の管理をする場合、価格を商品テーブルと売上テーブルに持たせてしまうと、価格という1つの事実を2つの場所で持っていることになる
Android通知のグルーピングを制御する

Androidの通知は、3つまでは独立して表示されますが、4つ以上たまると、アプリごとにまとめられてしまいます。（API Levelで挙動が変わる場合があります）

|通知3つまで|通知4つ以上|通知4つ以上|
|:--:|:--:|:--:|
|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/cc2ec18d-30d4-d7fa-6547-47ba7bf7ba6d.png)|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/e715227d-5f2e-fc51-3251-f2205aa365c8.png)|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/3e45fc02-98b1-c655-5d33-98db3e3b4d42.png)|

通知エリアが通知で埋まってしまうと、必要な通知も探せなくなってしまうので、アプリ単位でまとまるメリットもありますが、一つのアプリの全部の通知がまとまってしまうので、重要度の低い通知の中に重要度の高い通知が埋もれてしまうというデメリットもあります。
このグルーピング機能を制御する方法が用意されています。

https://developer.android.com/develop/ui/views/notifications/group?hl=ja

# 通知をまとめさせない

`setGroup()`でgroupを設定すると、自動でまとまらなくなります。

```kotlin
notificationManager.notify(
    id++,
    NotificationCompat.Builder(this, "channel1-1")
        .setSmallIcon(R.drawable.ic_small_icon)
        .setGroup("group2")
        .setContentTitle("1-2")
        .setContentText("text 1-2")
        .build()
)
```

いくつ通知しても、独立した通知のままです。

|group指定なし|group指定あり|
|:--:|:--:|
|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/e715227d-5f2e-fc51-3251-f2205aa365c8.png)|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/cc94acfa-7a92-1235-70ab-14b49bc62370.png)|


全部独立して通知がたまってしまうとユーザビリティ的にもあまり良い状態ではないですね。
アプリ単位でまとまってしまうと埋もれてしまうので避けたいのだけど、種別単位ぐらいでまとまってほしいところ。

groupを設定するとグルーピングされないというのはすこし奇妙ですが、本来は次のように、複数のまとまりに分けてグルーピングさせる機能です。

# グループ単位でまとめさせる

groupを設定した通知と、`setGroupSummary(true)`を設定した通知を送ることで、同じgroupでまとめることができるようになります。

```kotlin
notificationManager.notify(
    SUMMARY_ID, // 固定値
    NotificationCompat.Builder(this, "channel1-1")
        .setSmallIcon(R.drawable.ic_small_icon)
        .setGroup("group1")
        .setGroupSummary(true)
        .build()
)
notificationManager.notify(
    id++,
    NotificationCompat.Builder(this, "channel1-1")
        .setSmallIcon(R.drawable.ic_small_icon)
        .setGroup("group1")
        .setContentTitle("2-1")
        .setContentText("text 2-1")
        .build()
)
```

|通知3つまで|通知4つ以上|
|:--:|:--:|
|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/4c7a5e92-ae74-0457-6c7a-3b453fecfc95.png)|![](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/155171/2ed1ee5a-5619-3067-c6fa-e1ec490b5951.png)|

groupを設定していない通知は、これまでと同様に、4つ以上通知がたまるとアプリ単位でまとまるようになります。gropを設定していると、アプリ単位でまとまる通知には含まれなくなり、groupとsummaryを設定している場合は、2つ以上の通知があるとまとまるようになります。

複数の重要度の異なるカテゴリーの通知を行っている場合は、重要度の高い通知を独立させることで、ユーザーに気づいてもらいやすくでききるかもしれませんね。

※安易に全部を独立させて通知エリアを自分のアプリの通知で埋めてやるぜ、みたいなことはしないでくださいね。

以上です。
Djangoの日本語ドキュメントをローカルでビルドする方法

Django ドキュメントの翻訳は [Transifex](https://app.transifex.com/django/) プラットフォーム上で行うのですが、 `:ttag:`のような [Sphinx](https://www.sphinx-doc.org/ja/master/) 記法のプレビューができないので、うまくリンクが貼れているのかイマイチわかりません。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/352755/19d5a72a-9d12-8e38-7207-fd05dbba8cb2.png)

https://docs.djangoproject.com/ja/5.0/internals/contributing/writing-documentation/#how-to-start-contributing-documentation

公式👆を見ても英語ドキュメントのビルド方法しか書かれていなかったので、日本語でビルドする方法をメモしておきます。
（最新の翻訳されたドキュメントが読みたい場合にも役立つと思います）

## リポジトリのクローン
```bash
$ git clone https://github.com/django/django.git
$ git clone https://github.com/django/django-docs-translations.git

# 翻訳ファイルを最新のブランチに切り替えておきます
$ cd django-docs-translations
$ git checkout stable/5.0.x
```

## ファイルのコピー

下記のように、 `django/docs/locale/ja/LC_MESSAGES` の中に `django-docs-translations` リポジトリの中にある `.po` ファイルをコピーしておきます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/352755/911dbcea-07a4-7860-7686-bad63beec433.png)

ここに、チェックしたい対象の、 [Transifexのダッシュボード](https://app.transifex.com/django/django-docs/language/ja/) からダウンロードできる`.po`ファイルを上書きします。

## 仮想環境のセットアップ

ここは [公式](https://docs.djangoproject.com/ja/5.0/internals/contributing/writing-documentation/#how-to-start-contributing-documentation) と同じです。

```bash
$ cd ../django
$ python -m venv .venv
$ source .venv/bin/activate
$ python -m pip install -r docs/requirements.txt
$ cd docs
```

## ビルド

言語を指定するオプションを付けます（2024-02-20 修正）。

```bash
$ make LANGUAGE=ja html
```

しばらく待つと、`_build/html`の下にドキュメントが生成されます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/352755/b97c1405-3c29-62c6-1170-184091e3eb35.png)

リンクがおかしいところはターミナルでエラーが出るので、チェックしながら直していきます。
生成されたHTMLを見ながらリンクを実際にチェックすることもできます。
Ubuntu22.04 CLIでバーチャルホスト設定を行ったときに参照したサイト

<h3>1. 全体の流れ</h3>
https://qiita.com/i-tanaka730/items/3f28150eb1b3b7f8183c

<h3>2. ERROR: Site mysitename does not exist!への対処</h3>
https://qiita.com/mzmttks/items/85c69313693cb1df4949
フリーレン様、ベイズ推定とミミックに何の関係があるんですか？

# アニメ「葬送のフリーレン」23話

フェルン「フリーレン様、宝箱を判別する魔法（ミークハイト）の判別結果を見ましたよね？ミミックです」
フリーレン「フェルン、その魔法の精度は99%だよ」
フェルン「それがどうかしたのですか？」
フリーレン「ベイズ推定だよ」
フェルン「...ベイズ推定とミミックに何の関係があるんですか？」

※ 本記事ではベイズ推定を解説する関係上、原作とは異なる設定が登場します。予めご了承ください。

---

フリーレン「フェルン、私がここでこの宝箱を開けて、ミミックに食べられる確率は？」
フェルン「99%なんじゃないんですか？」
フリーレン「違うよフェルン。宝箱を判別する魔法（ミークハイト）の精度99%というのは、**実際にミミックに使ったときに、正しくミミックだと判別する確率**だよ [^1]。本物の宝箱に使ったときにミミックだと誤判定される場合が考慮されていない」
フェルン「それはそうかもしれませんが...だからと言って、その宝箱を開ける理由になるんですか？」
フリーレン「フェルン、この世界の宝箱の何%がミミックなのか知ってる？」
フェルン「何%なんですか？」
フリーレン「2%だよ [^2]。それはつまり、本物の宝箱に宝箱を判別する魔法（ミークハイト）を使って、ミミックだと誤判定されている確率も無視できない」

```mermaid
graph TD;
    実際はミミック --> ミミックと判定;
    実際は本物の宝箱 --> ミミックと判定;
    実際はミミック --> 本物の宝箱と判定;
    実際は本物の宝箱 --> 本物の宝箱と判定;
```

フェルン「なるほど...ではこの宝箱がミミックである確率はどのくらいなんですか？」
フリーレン「宝箱を判別する魔法（ミークハイト）が本物の宝箱を本物と判別する精度も99% [^3]。つまり1%の確率でミミックだと誤判定してしまうわけだよ。ミミックかどうか分からない宝箱に宝箱を判別する魔法（ミークハイト）を使ったときにはね、次の2パターンを考える必要があるんだ。

1. 実際はミミックで、かつそれを正しくミミックと判別する確率: 0.02 &times; 0.99 = 0.0198
2. 実際は本物の宝箱で、かつそれを間違えてミミックと判別する確率: 0.98 &times; (1 - 0.99) = 0.0098

これらの確率を比べてみてどう？
」

フェルン「確かに、値としては同程度のオーダーですね」
フリーレン「でしょ？ここから『ミミックと判定が出たときに、実際にミミックである』確率は

0.0198 / (0.0198 + 0.0098) &approx; 67%

ということになる。
」
フェルン「意外と低いですね。理屈としては分かるのですが、直観に少し反する結果ですね」
フリーレン「これはね、ミミックが本物の宝箱と比べて珍しいことが効いているんだ。ミミックが珍しいせいで、本物の宝箱からの誤判定率が優位になってきて、偽陽性（ミミックではないのにミミックと判断してしまうこと）が増えてしまう。こういう陽性が珍しいケースではね、陽性の珍しさ以上に判定精度を十分上げる必要があるんだ。現実でも、ガンの検査やAIによる異常検出のように、一見精度が高いから安心だと思えても、偽陽性が高くて使い物にならない場合が多くあるんだ」
フェルン「...最後はよくわかりませんでしたが、とにかく、99%という数字に騙されてはいけませんね」
フリーレン「そう。だからこの中身は貴重な魔導書だよ。私の統計学者[^4]としての経験がそう告げている」

&darr; &darr; &darr;

![0.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1752357/6d144580-8f74-e1ab-61d9-3dcaf4159de2.jpeg)

(画像元: [葬送のフリーレン公式Xアカウントのポスト](https://x.com/FRIEREN_PR/status/1722403663036211701?s=20)より)

[^1]: 本編の設定ではありません。
[^2]: これも本編の設定ではありません。
[^3]: これも当然本編の設定ではありません。
[^4]: これが本編の設定なわけがありません。
撮影した画像を読み込む【道具としての OpenCV 画像認識】

# 本記事でできること
画像を読み込んで画面に表示します。
![load_image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/37698/173e0456-4f59-d099-0f4e-2b859a51c53c.png)

# 想定シーン
## ロボットをビジュアルフィードバック制御する
カメラを使ったロボットアームの制御方法を、ビジュアルフィードバック制御といいます。ここでは、ビジュアルフィードバック制御を使った自動化システムを開発する際に必要となる画像認識プログラムをまとめています。

## 撮影した画像を読み込む
画像認識プログラムを実装する際、いきなりカメラからのライブ映像を処理するよりも、代表的な静止画に対して画像認識プログラムを作成してテストするほうが効率的です。ここでは、事前に用意しておいた画像を画面に出すだけのプログラムを掲載します。

# 実行環境
- OS：Ubuntu 22.04 LTS
- 言語：C++
- クルーボ：v5.1.0

## クルーボについて
ロボットアプリケーション開発には、株式会社チトセロボティクスのロボット制御ソフトウェア「クルーボ」を使用します。本記事のプログラムは、クルーボがインストールされた制御コンピュータ上で動作します。

- クルーボの製品サイト：https://chitose-robotics.com/product

## プログラム抜粋
```c++
cv::Mat load_image(const std::string file_path) {
    cv::Mat loaded_image = cv::imread(file_path, 1);
    if (loaded_image.empty()) {
        throw std::runtime_error("画像を正常に読み込めませんでした。");
    }
    return loaded_image;
}
```

## 全体プログラム
```c++
#include <iostream>
#include <opencv2/opencv.hpp>

cv::Mat load_image(const std::string file_path) {
    cv::Mat loaded_image = cv::imread(file_path, 1);
    if (loaded_image.empty()) {
        throw std::runtime_error("画像を正常に読み込めませんでした。");
    }
    return loaded_image;
}

int main(void) {
    std::string file_path = "../data/fuji.jpg";
    const cv::Mat loaded_image = load_image(file_path);

    cv::imshow("window", loaded_image);
    cv::waitKey(0);
}

```

## おわりに
人手作業をロボットアームで自動化するために、カメラを使ったロボット制御＝ビジュアルフィードバック制御が大切です。
ロボット制御用の画像認識でも中身のひとつひとつはシンプルなので、要素に分解して解説していきたいと思います。
# フリマアプリで販売手数料や販売利益を表示させたい（JavaScript）

# はじめに
プログラミング初心者です。
現在フリマアプリを作成中、終盤です。
今回アプリが完成し最終チェックをしていたところ、エラーが一つ飛び出てきたので記録します。

# JavaScriptで販売手数料や販売利益を表示させたい
今回のエラーとして、商品を出品する際に金額を入力すると販売手数料と販売利益が自動で出力される機能を実装したが、なんらかのエラーで保存がされなかった場合に前述の二つの項目が出力されなくなってしまうというものでした。
端的にコードを貼り付けて記録しちゃいます。
#### Before
```js
window.addEventListener('turbo:load', () => {

  const priceInput = document.getElementById("item-price");
  priceInput.addEventListener("input", () => {
    const inputValue = priceInput.value;

    const addTaxDom = Math.floor(inputValue * 0.1);
    const addTaxDomElement = document.getElementById("add-tax-price");
    addTaxDomElement.textContent = addTaxDom;

    const salesProfit = Math.floor(inputValue * 0.9);
    const salesProfitElement = document.getElementById("profit");
    salesProfitElement.textContent = salesProfit;
  });
};
```
#### After
```js
const price = () => {

  const priceInput = document.getElementById("item-price");
  priceInput.addEventListener("input", () => {
    const inputValue = priceInput.value;

    const addTaxDom = Math.floor(inputValue * 0.1);
    const addTaxDomElement = document.getElementById("add-tax-price");
    addTaxDomElement.textContent = addTaxDom;

    const salesProfit = Math.floor(inputValue * 0.9);
    const salesProfitElement = document.getElementById("profit");
    salesProfitElement.textContent = salesProfit;
  });
};

window.addEventListener("turbo:load", price);
window.addEventListener("turbo:render", price);
```
### 解説
訂正したのは以下の二つです。
１、コードを関数化し、最後の行で呼び出している。
２、ページがrenderされたときにも表示されるようにしている。（今回のエラー原因）
```js
window.addEventListener("turbo:render", price);
```
最後のこの行で、なんらかの不具合でエラーになり再度入力ることになった時、また販売手数料と販売利益が出力されるようになります。

今回は以上です。
[PRMLまとめ]1.1多項式フィッティング

# はじめに
先日、機械学習界隈では有名なパターン認識と機械学習(通称: PRML)を購入した。

[パターン認識と機械学習](https://amzn.to/4bLMxnv)

結構難解だという声も聞くが、機械学習をやる身としては理解しておいた方が良いので何とか読破しようと思う。ただ読むだけでは知識が定着しないので、読んだ内容をブログにまとめてアウトプットしていこうと思う。

また、PRMLの内容をまとめた資料として、松尾研の輪読資料もあるのでこちらも参考にしてもらいたい。

https://deeplearning.jp/seminar-2/#1646371993774-baeebddd-8411

# 1.1 多項式曲線フィッティング
### 訓練集合
訓練集合として、N個の入力値$X≡(x_1, x_2,...,x_N)$と入力値に対応する観測値$t≡(t_1, t_2, ..., t_N)$が与えられたとする

### 目標
新たな入力$x$が与えられた時の観測値$t$を予測することを目標とする

### 予測方法
以下のような多項式で予測することを考える


$$
y(x, \mathbf{w}) = w_0 + w_1x + w_2x^2 + ... + w_Mx^M = \sum_{j=0}^{M}w_jx^j
$$

* $y(x, \mathbf{w})$は$x$の非線形関数であるものの、$\mathbf{w}$に対しては線形である

### 予測方法の評価方法
$\mathbf{w}$を任意の値に固定した時、$y(x, \mathbf{w})$の値と訓練集合の$t$の値とのずれの大きさで評価する。ずれが小さいほど予測性能が高く、ずれを計算する関数を**誤差関数**と呼ぶ。
データ点$x_n$における予測値$y(x_n, \mathbf{w})$と対応する目標値$t_n$とのずれは二乗和誤差であり、下式となる

$$
E(\mathbf{w}) = \frac{1}{2}\sum^{N}_{n=1}\lbrace y(x_n, \mathbf{w})-t_n\rbrace^2
$$

$E(\mathbf{w})$が最小となるような$\mathbf{w}$を選ぶことで関数を最適化できる。

### 過学習について
以下の時に過学習が発生しやすい
* $y(x, \mathbf{w})$の次数$M$を大きくしすぎる
* データの数が少ない

過学習とは訓練データ非常によくあてはまるが新たなデータに対して正確な予測を行える汎化性能が低下する事象である。

過学習を抑制する方法として、**正則化**がある。正則化は誤差関数の係数が大きな値になることに対してペナルティを付与する。これにより係数が大きな値になることを抑制する。
2次の正則化の場合は**リッジ回帰**と呼ばれ、下式で表される。

$$
E(\mathbf{w}) = \frac{1}{2}\sum^{N}_{n=1}\lbrace y(x_n, \mathbf{w})-t_n\rbrace^2+\frac{λ}{2}||\mathbf{w}^2||
$$
$$
||\mathbf{w}^2|| =\mathbf{w}^T\mathbf{w}=w_0^2+w_1^2+...+w_M^2
$$

 $\frac{λ}{2}$は二乗和項と正則化項のどちらを重視するのかを調整する係数である。 $λ$の値を小さくしすぎると、過学習が抑制されづらくなる。逆に$λ$の値を大きくしすぎると係数が小さくなりすぎるため、データへの当てはまりが悪くなる。

 # おわりに
 次は1.2 確率論についてまとめる！

 # 関連記事
 
 https://qiita.com/sasshi_i/items/8faaf11a945956bb9a14

 https://qiita.com/sasshi_i/items/2af0a76b95176437f923
【警鐘】目に見えない文字でNGワードをすり抜ける


掲示板やコメント欄を作るときにNGワードを設定できるようにしたいとする。

仮にNGワードが「竹輪」だったとして、以下のように実装したとする。

```js:JSでの実装イメージ
if (text.includes('竹輪')) {
    alert('不適切なワードが含まれています！');
    return;
}
```

一見よさそうに見えるが、これでは以下が弾けない。

```text:
竹‌輪
```

なんら変哲もない竹輪という文字列だが、実際はこうなっている。

```
竹U+200C輪
```

竹と輪の間にゼロ幅非接合子が入っている。

https://ja.wikipedia.org/wiki/%E3%82%BC%E3%83%AD%E5%B9%85%E9%9D%9E%E6%8E%A5%E5%90%88%E5%AD%90

これにより、単純な文字列比較ではNGワードに引っかからなくすることが出来てしまう。

このような目に見えない文字は以下のサイトにあるように複数存在する。

https://invisible-characters.com/

## で？何を言いたいの？

NGワード対策って大変だよね。
ということだけ。
特に解決方法は提示しません。

## というか

仮に「竹‌輪」が弾けたとして
悪意あるユーザーは「竹.輪」とかで対応するだろうから
いたちごっこなんだよね。
【Rails】foreign_key: true を記述するかしないか

## はじめに
Userモデルと紐づいたProfileモデルを作成しようとしているところ。
User:Profile = 1:1 の関係にしたい為、t.referencesを追記。
~~~ruby:20240218073445_create_profiles
class CreateProfiles < ActiveRecord::Migration[6.0]
  def change
    create_table :profiles do |t|
      t.references :user, null: false
      t.timestamps
    end
  end
end
~~~
ここで疑問に思った事は、foreign_key: trueをとりあえず追加しておけ。という記事が多くて理由はなんやねん、という事。これについて解説。
foreign_keyについての詳細は省略。

## RubyとRailsのバージョン
- Ruby 3.1.3
- Rails 6.0.6.1
## 【結論】Railsの命名規則に従っていれば基本は不要
今回のケースのような場合はActive RecordがUserモデルと関連性があるって事は外部キーは'user_id'だよね。という感じで推測して自動でカラムを作成してくれます。(賢すぎ)
## foreign_key: trueが必要な場合とは?
Railsの命名規則から外れているケース（例えば自己結合を行う時）
User間のフォロー機能を実装したいとして、User:User = 1:1とする。
この場合中間テーブルとしてrelationshipを作成するとして、このまま何も指定しないとuser_idが２つ出来てしまう（どっちがフォローしているのか不明になってしまう）
これを解決する為にfollwing_idとfollower_idみたいにしたい時！！
（具体例）
user1→user2をフォローする時にfollwing_id = 1, follower_id = 2としたいが下記のようにforeign_key: { to_table: :users } foreign_keyを指定しなければ、Active Recodeはuserテーブルから外部キーを推測する事ができないはず。（references :userでない為）
~~~ ruby:20230815011533_create_relationships
class CreateRelationships < ActiveRecord::Migration[6.0]
  def change
    create_table :relationships do |t|
      t.references :following, null: false, foreign_key: { to_table: :users }
      t.references :follower, null: false, foreign_key: { to_table: :users }
      t.timestamps
    end
  end
end
~~~
## GPTにも聞いてみた
https://chat.openai.com/share/c5bf2798-88c7-43c0-a728-022920516488
## 最後に
自分なりに色々調べましたが、最後の方の説明が難しくて雑になってしまった感。。
間違っている部分、細く部分あれば教えてください。

## 参考文献
https://railsguides.jp/association_basics.html
https://qiita.com/ryouzi/items/2682e7e8a86fd2b1ae47
Ruby Silverの私が行った勉強方法

おはこんばんは！ なおぽんと申します🐹
この度、Ruby Silverに合格したため、どのような勉強を行って対策したかまとめました。
少しでも参考になれば嬉しいです！

## ステータス
- Rubyの経験は1年半程度
- 大学4年生

## 学習期間
- 2週間程度
- 学習時間は1日平均3時間程度

## 学習に使用したもの
- 「[[改訂2版]Ruby技術者認定試験合格教本)](https://amzn.asia/d/fwQ6EgC)」の巻末の基本問題と模擬試験
    - 1回目：学習開始時（どの程度点数取れるか）
    - 2回目：試験3日前（わからない部分を洗い出すため）
    - 3回目：試験の前日（わからない部分がないか最終確認）
- [Ruby Silver 模擬試験](https://github.com/ruby-association/prep-test/tree/version3)
    - 1回目：試験1週間前（試験の傾向確認&わからない部分の洗い出し）
    - 2回目：試験の前日（わからない部分がないか最終確認）
- [REx](https://rex.libertyfish.co.jp/)
    - 10回程度：安定して9割取れるようになるまで行う
    [![Image from Gyazo](https://i.gyazo.com/6441b5c9f6709a90907b19385388e379.png)](https://gyazo.com/6441b5c9f6709a90907b19385388e379)
    [![Image from Gyazo](https://i.gyazo.com/8564c50f0f19e96a3e943368aa6e0be6.png)](https://gyazo.com/8564c50f0f19e96a3e943368aa6e0be6)

## 学習方法
1. 上記の問題集を解く
2. わからなかったor間違えた問題の傾向を確認し、印などをつけておく
3. 2で印を付けた部分の解説を読んでから、コードを実際に写して動かしてみる
4. 理解が足りなければ、より詳しく調べる

## 学習前に大切なこと
- 受験日を学習前に決める：後回しにしないため
- 絶対合格すると、みんなに伝えること：モチベーション維持に重要なため
- 試験について他の方の学習方法や問題のまとめ記事を軽く読んでおくこと

## 感想
受験してよかったです！学習中に理解できていない部分があると認識でき、合格した後は「理解が深まった」と体験できたからです。本と公式の模擬試験の問題のわからない部分を無くしておくことで、試験の本番中に新たに出会う問題形式は10問程度でした。そのため、対策を掴んでしっかり学習を進めたら本番で合格点以上は持っていけると思います。精神科に通いながらの受験でしたが、Rubyを深く再学習できる本当に良い機会でした！

## 最後に
ここまでお読みいただき誠にありがとうございました！
受験しようか迷っていたり、学習方法どうしたら良いか困っている方の手助けになれたら嬉しいです🐹
ChakuraUIでreact-hook-formのバリデーションエラーが表示されない

# はじめに

ChakuraUIでreact-hook-formを使った際に時間がかかったのでまとめます

# 問題

以下のコードを実装したところ、なぜかSubmitしてもエラーが表示されませんでした

```tsx
              <Box>
                <FormLabel>学習時間</FormLabel>
                <Input
                  type="number" // 学習時間を数値として入力させる
                  {...register("time", {
                    required: "時間の入力は必須です",
                    valueAsNumber: true,
                    min: {
                      value: 0,
                      message: "時間は0以上である必要があります",
                    },
                  })}
                />
                {errors.time && (
                  <FormErrorMessage>{errors.time.message}</FormErrorMessage>
                )}
              </Box>
```

登録はうまくいっていました。

# 解決方法

以下のようにFormControlでそれぞれのフォームを囲い、`isValidation`を設定することで正しくエラーが表示されるようになりました

```tsx
<FormControl isInvalid={!!errors.time}>
  <FormLabel>学習時間</FormLabel>
  <Input
    type="number"
    defaultValue={0}
    {...register("time", {
      required: "時間の入力は必須です",
      valueAsNumber: true,
      min: {
        value: 0,
        message: "時間は0以上である必要があります",
      },
    })}
  />
  {errors.time && (
    <FormErrorMessage>{errors.time.message}</FormErrorMessage>
  )}
</FormControl>
```

TypeScriptで書いていて、`errors.time`が

```
Type 'FieldError | undefined' is not assignable to type 'boolean | undefined'.
  Type 'FieldError' is not assignable to type 'boolean | undefined'
```

とでてしまったので`!!`をつけています

# おわりに

公式ドキュメントをしっかりみてやることが大切でした

# 参考
AntDのMultiple-Cascaderのdefalutvalues

# 背景
Cascaderにmultipleオプションをつけた際にdefalutvaluesの記述がdocを見ても分かリませんでした。
ここに備忘録としてまとめます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/405182/44d49c4c-cec4-0858-6d56-f9338b9b9f84.png)

https://ant.design/components/cascader#cascader-demo-multiple

# sample ソース

```tsx
import React from "react";
import "./index.css";
import { Cascader } from "antd";

interface Option {
  value: string | number;
  label: string;
  children?: Option[];
  disableCheckbox?: boolean;
}

const options: Option[] = [
  {
    label: "Light",
    value: "light",
    children: new Array(20)
      .fill(null)
      .map((_, index) => ({ label: `Number ${index}`, value: index })),
  },
  {
    label: "Bamboo",
    value: "bamboo",
    children: [
      {
        label: "Little",
        value: "little",
        children: [
          {
            label: "Toy Fish",
            value: "fish",
            disableCheckbox: true,
          },
          {
            label: "Toy Cards",
            value: "cards",
          },
          {
            label: "Toy Bird",
            value: "bird",
          },
        ],
      },
    ],
  },
];

const onChange = (value: string[][]) => {
  console.log(value);
};

const App: React.FC = () => (
  <Cascader
    style={{ width: "100%" }}
    options={options}
    onChange={onChange}
    multiple
    maxTagCount="responsive"
    defaultValues={[["bamboo", "little"], [["light", 0]]]}
  />
);

export default App;

```

defaultValuesに二次元配列を指定し、親から子までのvalueを左から要素にすることで設定することができます。
```tsx
defaultValues={[["bamboo", "little"], [["light", 0]]]}
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/405182/682851b1-5aa2-f503-436e-1c29ddbc3ffd.png)
モデル駆動型アプリの新デザインは何が変わったの？【PowerApps】

## 何が変わったの？
見た目！

旧フォーム
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/fe6cb628-166b-d741-4671-df664714773f.png)

新フォーム
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/2514a785-aaee-91a7-a04c-d76741be5ce3.png)

旧ビュー
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/a2290b36-def7-2407-5868-00a6147e0bf7.png)

新ビュー
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2524942/f4374ea5-521f-8caf-fa29-040681ad9d77.png)


ちょっと変わったかな？くらい

## メリットは？
項目ごとの境界線がはっきりしている
　→どこを触ったらいいかわかりやすい
　　→**初めて使う方にやさしい**


## 旧画面であった要望
旧デザインでは
情シス「項目ごとの境界がわからないから線を引くことできる？」

と言われたことを思い出しました。

## 印象の違い

新デザインは好きです！
項目ごとの境目がはっきりしていて、パキパキとした印象。

旧デザインのもうひとつ前のレガシーと言われていた時代に若干戻った感じもします

旧デザインはミニマルで必要最低限のモノしかないためすっきりしていましたが
確かに比べてみるとのっぺりした感じを受けます



市民開発者が増えつつある今、「わかりやすい」「使いやすい」が重要視されていると考えられます


## 技術的な違いはある？
特にないです。

公式も見た目の変更ととのことです
https://learn.microsoft.com/ja-jp/power-apps/user/modern-fluent-design
Voltaを導入してみた

# 概要
自宅PC（Windows11）入れ替えに伴い、Node.jsのバージョン管理をどうしようかと思い、調べてみたところVoltaというものがあるようなので、使ってみました。
※Flutter CLIを入れようとしたらNode.jsで動作するようだったので、Node.jsのバージョン管理を調べなおしてみた。

# インストール
- [公式ホームページ](https://docs.volta.sh/guide/getting-started)からインストーラーをダウンロード
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1770163/2cd2db78-f117-c2c4-7efc-3c51bcf09f9c.png)

インストールはポチポチ押していくだけで完了。

# Node.jsのインストール
- 最新バージョン（LTS）のインストール
```
volta install node
```

- バージョン指定のインストール
```
volta install node@20.11.10
```

# 利用するバージョン固定
### Node.jsのバージョン固定
```
volta pin node@バージョン
```

### npmのバージョン固定
```
volta pin npm@バージョン
```

### package.json
nodeを利用するフォルダで上記コマンドを実行するとpackage.json内で利用するバージョンが固定されました。
```
"volta": {
  "node": "20.11.1"
}
```
```
> node --version
v20.11.1
```

当該フォルダ内では、グローバルで利用しているバージョンではなく、
固定したバージョンを利用するようになるそうです。

# 参考
- [公式ホームページ](https://docs.volta.sh/guide/getting-started)
- [NodeJSのバージョン管理ツールって結局どれ使えばええんや！](https://qiita.com/tak8_al/items/791e8d032bdc13a135de)
- [Voltaって結局何がすごいん！？](https://qiita.com/tak8_al/items/9baab2a2fe7f175cc9e0)
Java学習1

## 変数
+ データ型と変数名で変数宣言して変数を作る
```java
int length; //整数　lengthを宣言
length = 3; //length に3を代入
```
+ 型推論で変数を作る
```java
var length = 3; //lengthに3を代入して型推論
// 代入された値からデータ型が決まるので、宣言不要
```
## 演算子
特に変わった使い方はしてない
子コンポーネントからのイベントに応じて親コンポーネントの変数を直接更新する方法

子コンポーネントでは$emitを使用してイベントを発火し、親コンポーネントではそのイベントをリッスンしてメソッドで処理を引き受けます。
ですが、変数を代入するだけのメソッドを用意するのはだるいので、リッスンした値を親コンポーネントのテンプレート内で直接代入する方法を紹介します。

子コンポーネントのイベントを`$event`で取得するとこができるので、子コンポーネントから送信された値で親の変数を直接更新することができます。
```vuejs:ChildComponent.vue
<template>
  <button @click="$emit('child-clicked', '何かの値')">クリック</button>
</template>
```

```vuejs:親コンポーネント
<template>
  <ChildComponent @child-clicked="parentData = $event" />
</template>

<script>
import ChildComponent from './ChildComponent.vue';

export default {
  components: {
    ChildComponent
  },
  data() {
    return {
      parentData: ''
    };
  }
}
</script>
```
EmptyViewはレイアウトに一切影響しない(SwiftUI)

## はじめに

SwiftUIにおいて `EmptyView()` がレイアウトに影響を与えないか気になったので、検証しました。

## 環境

- OS: macOS Sonoma 14.2.1 (23C71)
- Swift: 5.9.2
- シミュレータ: iPhone 15 Pro Max (17.2)

## 検証コード

以下のコードを実行して検証しました。
`VStack` の `spacing` に `16` を指定したので、もしレイアウトに影響を与えるなら `Text` 同士の間隔が大きくなるなどするはずです。

```swift:ContentView.swift
import SwiftUI

struct ContentView: View {
    var body: some View {
        VStack(spacing: 16) {
            Text("Foo")

            Text("Foo")

            EmptyView()

            Text("Foo")

            EmptyView()
                .border(.red)

            Text("Foo")

            EmptyView()
                .frame(height: 8)
                .border(.blue)

            Text("Foo")
        }
    }
}
```

## 実行結果

検証コードの実行結果です。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/138245/7fce2ad5-f0e9-b557-547d-87ac348b745b.png" width=50%>

`EmptyView()` はレイアウトに影響を与えず、 `Text("Foo")` が等間隔に5つ並びました。

## おわりに

`EmptyView` はレイアウトに一切影響しないことがわかりました。
これを知っておくと、例えばオプショナルな `View` で `nil` の代わりに `EmptyView()` を返すことで、非オプショナルにできます。

またもし `EmptyView` がレイアウトに影響を与えるケースがあれば、コメントなどで教えてくださると嬉しいです。
AWS EC2 unused,unhealthy各ステータスの違い

## 背景
運用中のアプリケーションにおけるAWS ターゲットグループのヘルスチェック実施結果を確認した際に、ターゲットグループ配下のEC2インスタンスを停止することで、**unhealthy**ステータスとなるか確認したところ、**unused**ステータスとなったため、改めてヘルスチェックが示すステータス詳細を確認した。

## 各ステータスについて
AWSによると、unhealty状態とは下記の状態を指す。
>ターゲットはヘルスチェックに応答しなかったか、ヘルスチェックに合格しませんでした。

一方unused状態とは、次の状態を指していた。
>ターゲットがターゲットグループに登録されていないか、ターゲットグループがロードバランサーのリスナールールで使用されていないか、ロードバランサーに対して有効ではないアベイラビリティーゾーンにターゲットがあるか、ターゲットが停止または終了状態にあります。

### 結論
私自身、インスタンスを停止させることによる応答不可状態でもターゲットグループのヘルスチェックは**unhealthy**ステータスを返すと勘違いしていたが、実際そうではなくインスタンス停止状態による応答不可の場合は、**unused**ステータスを返すと知った。

### 参考
https://docs.aws.amazon.com/ja_jp/elasticloadbalancing/latest/application/target-group-health-checks.html
django-markdownxの拡張機能実装

こんにちは。
株式会社クラスアクト インフラストラクチャ事業部の大塚です。

前回、DjangoにMarkdown記法の実装を行いました。

https://qiita.com/ohtsuka-shota/items/66ca0127d2e1bfadd0f5

今回はこの環境に拡張機能を実装していきたいと思います。

# 実装
## 実装していないと・・・
例えば・・・
拡張機能を実装していない場合、マークダウンで以下のように記載をしてみます。
```
■コード

\```python
print("hello django-markdownx")
\```

■表

|  TH  |  TH  |
| ---- | ---- |
|  TD  |  TD  |
|  TD  |  TD  |
```
するとプレビューで以下のように表示されてしまいます。
意図された表記とは異なります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/e64e5f29-c150-5da7-ddde-6f6b1fff0823.png)

## 実装してみると
プロジェクトディレクトリにあるsettings.pyに以下の設定を追記します。
※前3行は以前追加したコードです。
```blogPJ/settings.py
# Blogに掲載する画像等の格納場所を設定
MEDIA_URL = "/media/"
MEDIA_ROOT = os.path.join(BASE_DIR, 'media')

MARKDOWNX_MARKDOWN_EXTENSIONS = [
    'markdown.extensions.extra',   
    'markdown.extensions.codehilite',
    'markdown.extensions.toc',    
    'markdown.extensions.nl2br',  
]
```

この設定に関する公式サイトは以下となります。

https://neutronx.github.io/django-markdownx/customization/#markdownx_markdown_extensions

https://python-markdown.github.io/extensions/#officially-supported-extensions

プレビューを見てみます。
表記が変わりました。想定通りのレイアウトになりましたね。
どの拡張機能を実装するとどのようなことが可能になるかは公式サイトを確認ください。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3219385/95ac73a4-7985-1821-8651-e99dd8e042ba.png)
grep 

# grep 'temporary password' /var/log/mysqld.log

管理者パスワードを設定されている

# 気づき
第２引数は何を示めしているのだろうか？

# grep
grepはfileで名前をしてされたファイルを検索して与えられたpatternにマッチする部分を含む行を探します。
デフォルトでは、grepはマッチした行を表示します。

# 出典
man grep

# 気づき
引数のファイルの'temporary password'の部分を表示されているのか。

# 出典
https://www.shoeisha.co.jp/book/detail/9784798161488
Q学習(Q-learning)

Q学習とは強化学習のTD学習のひとつである。

## Q値

Q値という名前の由来は、「統計学でのP値の次の文字ということでQ値」という説が有力。

```math: 
Q(s,a) = E [ \sum ^{\infty }_{t=0} \gamma ^{t} r_{t}|s_{0}=s,a_{0}= a ] 
```
- $Q(s,a)$は状態$s$で行動$a$をとった場合の$Q$値。
- $\gamma$は割引率で、将来の報酬の価値を現在の報酬よりも低く評価するための係数。（通常は$0$以上$1$以下の値で、$0.9$程度に設定されることが一般的。)
- $r_t$は時刻$t$における報酬を表す。


## Q学習手続き

(1) 全ての$Q$値を乱数により初期化する。
(2) 学習が十分進むまで以下を繰り返す。
(2-1) 動作の初期状態に戻る。
(2-2) 選択可能な行動からQ値に基づいて次の行動を決定する。
(2-3) 行動後、Q値を更新する。
(2-4) ある条件(目標状態、あるいは一定の時間経過)に至ったら、(2-1)に戻る。
(2-5) (2-2)に戻る。

## Deep Q-Network(DQN)

Q学習と深層学習を組み合わせたもの

# ε-greedy法

単にQ値が一番大きいものを選択するだけではQ学習はうまくいかない。もしそうすると、初期値の乱数でたまたま大きな値となった行動だけが常に選択されてしまい、いくら動作を繰り返してもそれ以外の行動が選択されることはない。

その対策として、ε-greedy法と呼ばれる方法がある。まずあらかじめεを$0$から$1$の間の適当な定数として決めておく。行動選択に際しては、$0$から$1$の間の乱数を生成し、この値がε以下であればランダムに行動を選択する。またεを超えていれば、Q値の大きいものに対応する行動を選択する。
systemctl

# MySQLサーバーの起動
```
systemctl start mysqld.service
```

## systemctl
システム管理者は、systemctl ユーティリティーを使用してシステムサービスを管理できます。実行中のサービスの起動、停止、再起動、ブート時に起動するサービスの有効化と無効化、利用可能なサービスのリスト表示、システムサービスのステータスの表示など、さまざまなタスクを実行できます
## 出典
https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/8/html/configuring_basic_system_settings/managing-system-services-with-systemctl_managing-systemd#:~:text=%E3%82%B7%E3%82%B9%E3%83%86%E3%83%A0%E7%AE%A1%E7%90%86%E8%80%85%E3%81%AF%E3%80%81systemctl%20%E3%83%A6%E3%83%BC%E3%83%86%E3%82%A3%E3%83%AA%E3%83%86%E3%82%A3%E3%83%BC%E3%82%92%E4%BD%BF%E7%94%A8%E3%81%97%E3%81%A6%E3%82%B7%E3%82%B9%E3%83%86%E3%83%A0%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9%E3%82%92%E7%AE%A1%E7%90%86%E3%81%A7%E3%81%8D%E3%81%BE%E3%81%99%E3%80%82%E5%AE%9F%E8%A1%8C%E4%B8%AD%E3%81%AE%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9%E3%81%AE%E8%B5%B7%E5%8B%95%E3%80%81%E5%81%9C%E6%AD%A2%E3%80%81%E5%86%8D%E8%B5%B7%E5%8B%95%E3%80%81%E3%83%96%E3%83%BC%E3%83%88%E6%99%82%E3%81%AB%E8%B5%B7%E5%8B%95%E3%81%99%E3%82%8B%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9%E3%81%AE%E6%9C%89%E5%8A%B9%E5%8C%96%E3%81%A8%E7%84%A1%E5%8A%B9%E5%8C%96%E3%80%81%E5%88%A9%E7%94%A8%E5%8F%AF%E8%83%BD%E3%81%AA%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9%E3%81%AE%E3%83%AA%E3%82%B9%E3%83%88%E8%A1%A8%E7%A4%BA%E3%80%81%E3%82%B7%E3%82%B9%E3%83%86%E3%83%A0%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9%E3%81%AE%E3%82%B9%E3%83%86%E3%83%BC%E3%82%BF%E3%82%B9%E3%81%AE%E8%A1%A8%E7%A4%BA%E3%81%AA%E3%81%A9%E3%80%81%E3%81%95%E3%81%BE%E3%81%96%E3%81%BE%E3%81%AA%E3%82%BF%E3%82%B9%E3%82%AF%E3%82%92%E5%AE%9F%E8%A1%8C%E3%81%A7%E3%81%8D%E3%81%BE%E3%81%99

### start
start コマンドを使用すると、現在のセッションでシステムサービスを起動できます。

現在のセッションでシステムサービスを起動します。
```js
# systemctl start <name>.service
```
<name> は、起動するサービスユニットの名前 (httpd.service など) に置き換えます。

### 出典
https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/8/html/configuring_basic_system_settings/managing-system-services-with-systemctl_managing-systemd#:~:text=start%20%E3%82%B3%E3%83%9E%E3%83%B3%E3%83%89%E3%82%92,%E3%81%8D%E6%8F%9B%E3%81%88%E3%81%BE%E3%81%99%E3%80%82

# MySQLサーバーのステータスを確認
```
systemctl start mysqld.service
```

### status
サービスユニットを検査して詳細情報を取得し、サービスの状態 (ブート時の起動が有効かどうか、現在実行中かどうか) を確認できます。特定のサービスユニットの前または後に起動するように指定されたサービスを表示することもできます。

手順

systemctl コマンドを使用して、次のタスクのいずれかを実行します。

システムサービスに対応するサービスユニットに関する詳細情報を表示します。
```
$ systemctl status <name>.service
```
<name> は、確認するサービスユニットの名前 (gdm など) に置き換えます。

このコマンドでは、以下の情報が表示されます。

* 選択したサービスユニットの名前とその後に続く簡単な説明
* 利用可能なサービスユニットの情報 で説明されている 1 つ以上のフィールド
* サービスユニットの実行: ユニットが root ユーザーによって実行される場合
* 最新のログエントリー
### 出典
https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/8/html/configuring_basic_system_settings/managing-system-services-with-systemctl_managing-systemd#:~:text=%E3%82%B5%E3%83%BC%E3%83%93%E3%82%B9%E3%83%A6%E3%83%8B%E3%83%83%E3%83%88%E3%82%92%E6%A4%9C%E6%9F%BB,%E6%9C%80%E6%96%B0%E3%81%AE%E3%83%AD%E3%82%B0%E3%82%A8%E3%83%B3%E3%83%88%E3%83%AA%E3%83%BC
長テーブルのうなぎ屋 Python3編 解答 paizaラーニング

# 問題
長テーブルのうなぎ屋 (paizaランク B 相当)
https://paiza.jp/learning/long-table

# 解答
```python:unagiya.py
def is_ocupied_seats(num, place):
    for i in range(place, place+num):
        if seats[i%n] == True:
            return False
    return True

n, m = map(int, input().split())
seats = [False] * n

for _ in range(m):
    num, place = map(int, input().split())
    place -= 1
    if is_ocupied_seats(num, place):
        seats[place:place+num] = [True]*num
    # print(seats, is_ocupied_seats(num, place), place, num)
print(seats.count(True))
```
【AWS】セキュリティグループのアウトバウンドの「0.0.0.0/0」


## はじめに
AWSのEC2インスタンスなんかに付与するセキュリティグループを作成する際、「インターネットにアクセスする場合、アウトバウンド通信は0.0.0.0/0を指定します」なんて書かれていることが多いが、いつも「ふ〜ん」という感じで設定しており、よく理解していなかった。

## つまり、、、

例えば何らかのパッケージのインストールをする場合、「0.0.0.0/0」を指定する必要がある。
これは結局、そのパッケージのインストール元のIPアドレスがわかっていれば、それを指定すればよい。

ただ、実際にはわからない（ことはないと思うが、いちいち指定するのは面倒くさい）ので、「0.0.0.0/0」を指定することで、全てのアドレスへのアクセスを許可している。

ここで、「なんでインバウンドで許可していないのに戻りの通信が戻ってこれるんだ？」と思っていたが、<font color="red">セキュリティグループはステートフル</font>なため、インバウンドで許可したらアウトバウンドで設定する必要はないし、アウトバウンドで許可したらインバウンドで許可する必要はない。

これと対照的なのがネットワークACL。
<font color="red">ネットワークACLはステートレス</font>なため、インバウンドで許可したらアウトバウンドも許可しないと通信が戻っていけないし、逆にアウトバウンドで許可したらインバウンドも許可しないと戻りの通信が戻ってこれなくなる。

## おわりに

かなり初歩的なことだが理解していなかった。
理解できてスッキリ。

### 参考

https://dev.classmethod.jp/articles/ec2-cacess/

https://www.seeds-std.co.jp/blog/creators/2022-02-02-194955/

https://repost.aws/ja/knowledge-center/connect-http-https-ec2
Unity - TextMeshProのcolorタグがフォントマテリアルのFaceと混じる時の回避方法

とんでもなく久しぶりの記事になっちゃいましたが、自分の備忘録も兼ねて困った事象の解決手段を残しておきます。

# 何が起きたのか
起きた事象としては... **colorタグで指定してるのに色が変わらない！**
↓こんな感じ。(「ゲーム」部分が赤くなってほしい)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/62924/dd3897f8-ea66-8f96-6964-337915292d1f.png)

これは以下の条件下で発生しました。
- プリセットのフォントマテリアルのFace - Colorで文字色を変えていた
- colorタグで文字色を変えようとした

# 回避方法
どういうこっちゃ、プリセットのフォントマテリアルって何よ...?
という方は下の方に前提知識をメモしておきましたので、そちらをどうぞ。

さて、これはタイトル通り`color`タグとマテリアルのFace - Colorの色が競合...というより混じってしまうことで発生するようです(加算とか合成とかだと思います)。

自分はこの問題に対して、`font`タグで変えたい色を設定したフォントマテリアルを指定することでやりたいことを実現できました。

`font`タグを使うと、一部だけ使用するマテリアルを変えることができます。
```C#
textMeshProGUI.text = "楽しい<font="フォント名" material="フォントマテリアル名">ゲーム</font>開発";
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/62924/b246d40f-4df0-3798-9639-84326d47a673.png)

# 前提
今回の話題で出てきた機能の簡単な解説を載せます。

## TextMeshProはcolorタグで色を変えられる
以下のように`TextMeshProGUI`のtextに`color`というタグを指定すると、指定した部分の文字色を変更することができます。
```C#
textMeshProGUI.text = "楽しい<color=red>ゲーム</color>開発";
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/62924/8ee3c536-4402-212f-f42a-ecba69edb6c8.png)

## フォントマテリアルのFace項目のcolorでも色が変えられる
TextMeshProでは、フォント装飾をマテリアルで定義できる機能があります。
この中で、Face - Colorの項目で文字色が変えられます。
| フォントマテリアル設定 | 表示結果 |
| --- | --- |
| ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/62924/af5e53a8-3d9e-421c-79f3-3467fc493ea9.png) | ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/62924/859faf16-9c20-a30c-aa3c-a5a23c699c5a.png)

## フォントマテリアルのプリセット機能
TextMeshProでは、フォントマテリアルをプリセットとして作成することができます。
例えば、「白いアウトラインをつけた黒文字」が設定されたマテリアルを作成することができます。

プリセットの詳しい作成方法は、他でたくさん説明されていると思うのでここでは割愛です。

## TextMeshProの運用方法
プリセットを使うと、そのマテリアルをTextMeshProGUIコンポーネントの`Material Preset`に設定してあげればすぐにそのスタイルを適用することができます。
この使用方法は、個人的には以下のようなメリットがあると思っております。
- 便利
- 一括で色を変えたいときには、プリセットのフォントマテリアルを変えてあげるだけで、使用している箇所全体の表示を変更できる


# まとめ
パッと検索した限りでこのことに言及している記事を見つけられなかったので、ババっと書いてみました。
誰かの助けになるかもしれないと信じて...

ちょっとした宣伝です。
スマホ向けRPG「Non Eternals」開発中！

https://twitter.com/asiramasiram/status/1714609772421316745
【python】乃木坂46でクラスの継承を勉強する

# 乃木坂46でクラスの継承を勉強する

## はじめに
乃木坂46のメンバーで「自転車を運転する」、「自転車にブレーキをかける」というクラスを実装し、継承させて「電動自転車を運転する」というクラスを作ります。

## 自転車クラス
自転車クラスのソースコードです

```python
class Bycycle:

  # コンストラクタ
  def __init__(self,name="人"):

    self.__name = name



  # getter Div
  # getter name
  @property
  def getName(self):
    return self.__name

  @getName.setter
  def setName(self,set_name):
     if len(set_name) > 0:
        self.__name = set_name


  def riding(self,set_name):
    print(f"{set_name}は自転車を漕ぐ")

  def breaking(self,set_name):
    print(f"{set_name}はブレーキをかけて止まる")
```

## 電動自転車クラス
次に自転車クラスを継承させて電動自転車クラスを実装します。

```python
from bycycle import Bycycle

class ElectricBycycle(Bycycle):

  def electronic_ride(self,set_name):

    print(f"{set_name}は電動自転車を漕ぐ")
```

## インスタンスを作って実行したソースコード
次に自転車クラス、電動自転車クラスからインスタンスを呼び出し、実行するソースコードです

```python
from bycycle import Bycycle
from bycycle_electrnic import ElectricBycycle

by1 = Bycycle("梅澤美波")
by1.setName = "山下美月"
driver_name1 = by1.getName
by1.riding(driver_name1)
by1.breaking(driver_name1)

by2 = Bycycle()
by2.setName = ""
driver_name2 = by2.getName
by2.riding(driver_name2)
by2.breaking(driver_name2)

eby = ElectricBycycle()
eby.setName = "久保史緒里"
driver_name3 = eby.getName
eby.riding(driver_name3)
eby.breaking(driver_name3)
eby.electronic_ride(driver_name3)
```

## 実行した結果
実行した結果の画像です。

![result.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1055346/94d9858f-a1cd-fb39-847b-eb8195fa6100.jpeg)


## 最後に

クラスの継承は、**「差分プログラミング」**　と呼ばれる、元のクラスから差分のメソッドを追加して実装するので楽ですね。
配列の中に入っているハッシュの値が大きい順に並び替える

## やりたいこと
配列の中に入っているハッシュの値が大きい順に並び替えたい。

```ruby
[{:name=>"player1", :count=>21},
{:name=>"player2", :count=>0}, 
{:name=>"player3", :count=>30}]
```
このように並び替えたい。↓
```ruby
[{:name=>"player3", :count=>30}, 
{:name=>"player1", :count=>21}, 
{:name=>"player2", :count=>0}, ]
```
## 考えたこと
「配列の要素を並び替えるのにsortメソッドというのがあったはず。sortメソッドを使えば並び替えられるかな」

## 試したこと
公式リファレンスをもとに`sort`メソッドを使ってみる。  
今回は各要素がハッシュの形をしており、`:count`キーの値を比較する。
```ruby
a = [{:name=>"player1", :count=>4},
 {:name=>"player2", :count=>28},
 {:name=>"player3", :count=>20},
 {:name=>"player4", :count=>0}]
 
a.sort do |a, b|
  a[:count] <=> b[:count]
end
```
`:count`キーの値が小さい順に並び替えることができた。
```ruby
=> 
[{:name=>"player4", :count=>0},
 {:name=>"player1", :count=>4},
 {:name=>"player3", :count=>20},
 {:name=>"player2", :count=>28}]
```

破壊的メソッド`sort!`で配列そのものを並び替えたあと、`reverse`メソッドを使うと大きい順に並び替えることができた。
```ruby
irb(main):038* a.sort! do |a, b|
irb(main):039*   a[:count] <=> b[:count]
irb(main):040> end
=> 
[{:name=>"player4", :count=>0},
 {:name=>"player1", :count=>4},
 {:name=>"player3", :count=>20},
 {:name=>"player2", :count=>28}]
irb(main):041> a.reverse
=> 
[{:name=>"player2", :count=>28},
 {:name=>"player3", :count=>20},
 {:name=>"player1", :count=>4},
 {:name=>"player4", :count=>0}]
```

## 失敗例1
`reverse`メソッドをつなげて大きい順に並び替えようとするとできない。
```ruby
a.sort.reverse do |a, b|
irb(main):029*   a[:count] <=> b[:count]
irb(main):030> end
(irb):28:in `sort': comparison of Hash with Hash failed (ArgumentError)
```

## 失敗例2
`sort_by`メソッドで同じことをやろうとするとできない。(`sort_by!`メソッドでも同じ結果になる)
```ruby
irb(main):046* a.sort_by do |a, b|
irb(main):047*   a[:count] <=> b[:count]
irb(main):048> end
(irb):47:in `block in <top (required)>': undefined method `[]' for nil (NoMethodError)
```

## 成功例2
ブロックパラメータの数（ブロックに渡す数）を1つにすると、`sort_by`でも並び替えることができる。
```ruby
irb(main):052* a.sort_by do |a|
irb(main):053*   a[:count]
irb(main):054> end
=> 
[{:name=>"player4", :count=>0},
 {:name=>"player1", :count=>4},
 {:name=>"player3", :count=>20},
 {:name=>"player2", :count=>28}]
```

## 学んだこと
`sort`メソッドはブロックパラメータに2つの要素を渡せるが、`sort_by`メソッドは1つしか渡せない。

## 参考記事
[Ruby公式リファレンス(sort)](https://docs.ruby-lang.org/ja/latest/method/Enumerable/i/sort.html)
[Rubyの配列の中のハッシュのソート](https://qiita.com/shy_azusa/items/4c761d4391b1fca2e718)
誤差逆伝播法を計算グラフで理解する

社内で誤差逆伝播法についての勉強会がありました。
その際の発表資料です。
学生時代では、誤差逆伝播法は数式のみで勉強しましたが、
計算グラフで捉えるとより分かりやすかったです。
プログラムの実装でも、forward(順伝播)とbackword(逆伝播)さえ定義すればいいのも魅力的ですね。

<script defer class="speakerdeck-embed" data-id="e2a540dd98ec4aa78a41c58c78e647f4" data-ratio="1.7777777777777777" src="//speakerdeck.com/assets/embed.js"></script>
QiitaでTree構造のような目次の作り方

---
QiitaでTree構造のような目次の作り方
---

**参考目次**
1. [サブタイトルとは何か](#1-サブタイトルとは何か)
   - [1.1 サブタイトル](#11-サブタイトル)
   - - [1.1.1 サブサブタイトル](#111-サブサブタイトル)
   - - - [1.1.1.1 サブサブサブタイトル](#1111-サブサブサブタイトル)
   - - - - [1.1.1.1.1 サブサブサブサブタイトル](#11111-サブサブサブサブタイトル)
   - - - - - [1.1.1.1.1.1 サブサブサブサブサブタイトル](#111111-サブサブサブサブサブタイトル)
   - [1.2 サボタイトル](#12-サボタイトル)
2. [サブ](#2-サブ)

## 1. サブタイトルとは何か

### 1.1 サブタイトル

#### 1.1.1 サブサブタイトル

##### 1.1.1.1 サブサブサブタイトル

##### 1.1.1.1.1 サブサブサブサブタイトル

##### 1.1.1.1.1.1 サブサブサブサブサブタイトル

### 1.2 サボタイトル

## 2. サブ


<font color="low blue">**はじめに**</font>

　Qiitaの記事を書いていた際、ふと他のサイトと見比べて目次にtree構造がないことに気がつきました。

　なので今回は擬似的に作ってみて、それっぽいTree構造の目次を作成する方法を紹介できればと思います。

<font color="low blue">**目次の基本**</font>

　Markdownで目次を作成する基本は、リンクとリストを組み合わせることです。以下のように、見出しに対応するアンカーリンクを作成し、それらをリスト形式で並べることで目次を作成します。

```markdown
1. [サブタイトルとは何か](#1-サブタイトルとは何か)
2. [サブ](#2-サブ)
```

<font color="low blue">**Tree構造の目次の作り方**</font>

　Tree構造の目次を作るには、サブセクションをリストの階層として追加します。サブセクションへのリンクも、メインセクションと同様に作成します。

```markdown
1. [サブタイトルとは何か](#1-サブタイトルとは何か)
   - [1.1 サブサブタイトル](#11-サブサブタイトル)
   - [1.2 サブサブサブタイトル](#12-サブサブサブタイトル)
2. [サブ](#2-サブ)
```


<font color="low blue">**サブセクションの見出し例**</font>

```
## 1. サブタイトルとは何か
### 1.1 サブサブタイトル
### 1.2 サブサブサブタイトル
```

　因みに最初に書いた例は

```markdown
**参考目次**
1. [サブタイトルとは何か](#1-サブタイトルとは何か)
   - [1.1 サブタイトル](#11-サブタイトル)
   - - [1.1.1 サブサブタイトル](#111-サブサブタイトル)
   - - - [1.1.1.1 サブサブサブタイトル](#1111-サブサブサブタイトル)
   - - - - [1.1.1.1.1 サブサブサブサブタイトル](#11111-サブサブサブサブタイトル)
   - - - - - [1.1.1.1.1.1 サブサブサブサブサブタイトル](#111111-サブサブサブサブサブタイトル)
   - [1.2 サボタイトル](#12-サボタイトル)
2. [サブ](#2-サブ)

## 1. サブタイトルとは何か

### 1.1 サブタイトル

#### 1.1.1 サブサブタイトル

##### 1.1.1.1 サブサブサブタイトル

##### 1.1.1.1.1 サブサブサブサブタイトル

##### 1.1.1.1.1.1 サブサブサブサブサブタイトル

### 1.2 サボタイトル

## 2. サブ
```

のようになっています。

<font color="low blue">**おわりに**</font>

　なんかこれじゃない感ありますが、活用できる時は使っていこうと思いました。

　キになる記事を書けるように頑張っていきたいです。