OmniAICreator/Qiita-1.07M huggingface dataset:
PoseFix: Correcting 3D Human Poses with Natural Language

# PoseFix: Correcting 3D Human Poses with Natural Language
ICCV 2023
[paper](https://openaccess.thecvf.com/content/ICCV2023/papers/Delmas_PoseFix_Correcting_3D_Human_Poses_with_Natural_Language_ICCV_2023_paper.pdf)
[github](https://github.com/naver/posescript)

## 概要
PoseFixは、自然言語による指示を用いて3Dヒューマンポーズを修正するための新しいデータセットと手法を提案している．この研究は、特にフィットネスアプリケーションや家庭内での物理療法、デジタルアニメーションの支援など、多岐にわたる応用が期待される．PoseFixデータセットは、数千の3Dポーズとその修正方法を記述したテキストフィードバックのペアで構成されており、以下の二つのタスクに対して評価を行っている：
1. **テキストベースのポーズ編集**: クエリポーズとテキスト修正指示を与えて、修正された3Dボディポーズを生成するタスク
2. **修正テキスト生成**: 二つのボディポーズの違いに基づいて修正指示を生成するタスク

:::note info
昨今の進化がすごい言語系のモデルを、他のタスクとうまく組み合わせることができると、さらに別のアプローチが開発できる可能性は十分あるはず
:::

## 従来手法との比較
従来の手法では、3Dヒューマンポーズと自然言語の関係を探る試みがいくつか行われてきたが、3Dボディポーズの違いを説明することに焦点を当てたものはなかった．たとえば、テキスト記述を用いてモーションを生成する研究や、合成2Dレンダリングからポーズの違いを説明する研究があるが、3Dポーズペアにテキスト指示を関連付けるデータセットは存在しなかった．PoseFixは、このギャップを埋めるために、より多様なシーケンスからポーズを収集し、実際の3Dデータに基づいたテキストアノテーションを提供している．

## 新規性
PoseFixの新規性は以下の点にある：
1. **ペアでの3Dポーズとテキストフィードバック**: PoseFixデータセットは、3Dポーズペアとそれらの違いを説明するテキストフィードバックを含んでおり、修正指示を生成するための基盤を提供している．
2. **自由形式のフィードバック**: 固定的なテンプレートではなく、自由形式の自然言語でポーズの修正指示を生成することができる．
3. **多様なデータソース**: AMASSデータセットからの多様なポーズシーケンスを利用し、フィードバックの質と多様性を高めている．

## 方法論
- **ペア選択プロセス**: 同一シーケンス内のポーズペア（in-sequence）と異なるシーケンスからのポーズペア（out-of-sequence）を選択．異なるシーケンスからのペアは、一般化を助け、異なるスタイルの類似ポーズを学習するために使用される．
- **アノテーション収集**: Amazon Mechanical Turkを使用して、英語話者のアノテーターからテキスト修正指示を収集．指示は、各ポーズの異なる視点からのレンダリングを表示し、10ワード以上の詳細な説明を求めた．
- **自動生成**: 低レベルのポーズ特徴を使用して、自動的に修正指示を生成するパイプラインを設計．これにより、短時間で大量のアノテーションを生成することが可能になった．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/3a69fa07-65c3-9b7d-a3c2-05e9ab37b0ff.png)

## 結果と評価
PoseFixデータセットを用いた評価では、テキストベースのポーズ編集と修正テキスト生成の両タスクにおいて有望な結果が得られた．
- **テキストベースのポーズ編集**: クエリポーズとテキスト修正指示を入力とする条件付きVAE（cVAE）を使用して、新しいポーズを生成．結果は、ELBO、MPJE、MPVE、ジオデシック距離などの評価指標で測定された．
- **修正テキスト生成**: 自己回帰型トランスフォーマーモデルを使用して、修正指示を生成．評価はBLEU-4、Rouge-L、METEOR、R-precisionなどの自然言語処理指標で行われた．

## 結論
PoseFixは、3Dヒューマンポーズを自然言語による指示で修正するための新しいデータセットと手法を提案している．この研究は、フィットネスやデジタルアニメーションなどの応用分野で大きな可能性を秘めており、今後の研究の基盤となることが期待される．
論文読み：Segment Anything: A New Paradigm for Image Segmentation

# Segment Anything: A New Paradigm for Image Segmentation
ICCV 2023
[Project Page by Meta AI](https://segment-anything.com/)
[Paper](https://openaccess.thecvf.com/content/ICCV2023/papers/Kirillov_Segment_Anything_ICCV_2023_paper.pdf)
[github](https://github.com/facebookresearch/segment-anything)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/e04d4068-2762-9e7c-8f69-6e95d971b352.png)

:::note info
とりあえずProject Pageのdemoを試してみてください！
モデルのすごさが分かります！
:::


## 概要
Segment Anything (SA)プロジェクトは、新しいタスク、モデル、およびデータセットを用いた画像セグメンテーションのための基盤モデルを提案している．本プロジェクトでは、効率的なモデルをデータ収集ループに組み込み、1億以上のセグメンテーションマスクを含む史上最大のセグメンテーションデータセットを構築した．このモデルは、プロンプトエンジニアリングを通じて、新しい画像分布やタスクへのゼロショット転移を可能にするよう設計・訓練されている．多くのタスクにおいて、ゼロショットでのパフォーマンスは驚くほど高く、従来の完全教師あり学習モデルと競合するか、上回ることがある．

## 従来手法との比較
従来の画像セグメンテーション手法には以下のような問題があった：
- **限定されたデータセット**: 大規模なセグメンテーションデータセットが存在せず、特定のタスクやデータ分布に対するゼロショット転移が困難であった
- **柔軟性の欠如**: 特定のタスクに特化したモデルが多く、他のタスクへの応用が難しかった
- **リアルタイム性の欠如**: インタラクティブな使用に適したリアルタイム性能を持つモデルが少なかった

## 新規性
Segment Anythingの新規性は以下の点にある：
1. **プロンプト可能なセグメンテーションタスク**: 画像内の任意のセグメンテーションプロンプトに対して、有効なセグメンテーションマスクを返すタスクを定義している
2. **Segment Anything Model (SAM)**: 画像エンコーダ、プロンプトエンコーダ、マスクデコーダの3つのコンポーネントからなるモデルで、リアルタイムでのインタラクティブな使用が可能であり、曖昧さに対処できる
3. **データエンジン**: 自動データ収集を支援する効率的なモデルを用いて、1億以上のセグメンテーションマスクを収集するデータエンジンを構築している

## 方法論
- **プロンプト可能なセグメンテーションタスク**: プロンプトとして、前景/背景の点、粗いボックスやマスク、自由形式のテキストなどを使用できる．モデルは、これらのプロンプトに基づいて有効なセグメンテーションマスクを返す
- **SAMの設計**: 画像エンコーダが画像埋め込みを計算し、プロンプトエンコーダがプロンプトを埋め込み、軽量なマスクデコーダがセグメンテーションマスクを予測する．プロンプトエンコーダとマスクデコーダは、ウェブブラウザ上で50ms以内に実行される
- **データエンジン**: 手動支援、半自動、および完全自動の3つのステージでデータ収集を行い、最終的に1億以上の高品質なセグメンテーションマスクを生成する

## 結果と評価
Segment Anythingは、COCO、ADE20K、LVISなどのセグメンテーションベンチマークにおいて、高品質なマスクを生成し、ゼロショット転移で優れた性能を発揮している．たとえば、COCOデータセットでは、SAMは従来の手法と比較して高い精度を示し、多くのタスクにおいて競争力のある性能を達成している．

## 結論
Segment Anythingプロジェクトは、画像セグメンテーションの基盤モデルを構築するための新しいタスク、モデル、およびデータセットを提案している．このアプローチにより、ゼロショットでのタスク適応が可能となり、多くの応用分野で高い性能を発揮することが期待される．SAMとSA-1Bデータセットのリリースにより、今後のコンピュータビジョン研究の進展が期待される．

## githubのコード試す時
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/d9a5cae2-208b-0bcf-30be-0c9b26999077.png)

入力：
- セグメントしたい画像
- segmentation promptのいずれか

出力：
- segmentのmask領域
【Salesforce】フロービルダーのカスタムエラー

Salesforceのフロービルダーのカスタムエラーを使ってみる記事です。

## 「カスタムエラー」

#### エラーメッセージのカスタマイズ
特定の条件が満たされない場合に、ユーザーに対してメッセージを表示することができます。

#### デバッグの容易化
エラーの発生場所や原因を明確にすることで、フローのトラブルシューティングがしやすくなります。

#### ユーザーエクスペリエンスの向上
カスタムエラーを設定することで、ユーザーに適切なガイダンスを提供し、エラー発生時の混乱を最小限に抑えることができます。

https://help.salesforce.com/s/articleView?id=sf.flow_ref_elements_custom_error.htm&type=5

入力規則はシンプルな条件を検証するのに適していますが、複雑なロジックを実装するにはフロービルダーのカスタムエラーの方が適しています。
例えば、複数のオブジェクトにまたがる条件や特定の順序での処理が必要な場合です。

今回は、入力規則で手が届かないときを想定して、カスタムエラーで実装してみます。

## 要件
商談にはカスタムオブジェクトの「担当」と「タイムチャージ」が登録される。
「タイムチャージ」は商談の「担当」の登録ユーザーのみ作成できる。

### 「担当」オブジェクトを用意
商談とユーザーの参照関係も作成します。
![01担当.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/49cb3eb0-0dd5-fb80-35a7-e3be79a201a0.png)

### 「タイムチャージ」オブジェクトを用意
同じく、商談とユーザーの参照関係も作成します。
![02タイムチャージ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/216dd3fc-43ab-2727-4335-f230a16acf8a.png)

### 商談とのリレーション
リレーションはこんな感じです。
![03ER.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/a57d0b63-0fd6-a88a-f6b4-4f93fb53cfce.png)

### 商談に「担当」を作成
担当Aを作成します。
![04商談A.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/ba35720d-8432-01b3-5dc1-95c50ee8c56c.png)

### フロー
作成したフローはこんな感じです。
タイムチャージが作成されたときに、起動するレコードトリガーフローです。
関連する「担当」を取得してループ内で、同じユーザーかを判定します。
![05フロー.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/8bc64a1e-14a3-b673-28d1-a2fbc4cc4114.png)

### カスタムエラー
エラーメッセージは任意の記述ができます。
![06カスタムエラー.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/2d5906eb-db71-6aa4-b26a-0169e3c24aea.png)

### 「担当」ユーザー
ユーザー坂本直子さんを登録します。
![07担当A.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/19645f09-3acd-a56b-fa95-44b1f0747eda.png)

### 「担当」ユーザーと別のユーザーでエラー
無事にエラーメッセージが反映されました。
![08エラーメッセージ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/789516/1a068451-8f20-f248-7d76-ba04f5fb1886.png)

### まとめ

他にも、新しい商談を作成する際に、関連する取引先の特定の項目が空であればエラーを表示するような複雑な条件はフローで設定し、カスタムエラーを表示することで実現できそうです。

いかがでしたでしょうか。

今回は入力規則で手が届かないときを想定して、カスタムエラーで実装してみました。
フロービルダーのカスタムエラーを使ってみたい方へのご参考になれば幸いです。
会議のファシリテーションにおいて大切なこと

## はじめに
最近会議のファシリテーションをするようになり、なかなか難しいものだなと感じています。ファシリテーションは経験値が重要なスキルではありますが、知識や考え方を身につけることで上達するものでもあると思います。
今回は、私なりにファシリテーションにおいて大切なことをまとめてみました。

## 会議の目的とゴールを明確にする
会議には当然開催する目的があります。しかし、プロジェクト開始直後の何も固まっていないタイミングでの会議やマンネリ化した定例会などは、目的が不明瞭、または見失ってしまいやすいです。
また、目的は明確になっていても、ゴールまでは定義していないケースも多くあると思います。
会議は、全員が同じ会議の目的とゴールを認識し、同じ方向を向いて進んでいくことが重要です。
そのためには、まずファシリテーターの中で目的とゴールが明確になっている必要があります。そして、それをメンバーに共有して共通認識を作ることが重要です。
これによって、会議があるべき方向に進みやすくなり、有意義なものになります。


## 資料ベースで会話する
基本的なことではありますが、打ち合わせ資料は非常に重要です。
人間は耳から入る情報よりも目から入る情報の方が処理しやすいものなので。
資料がない状態で口頭だけで会話すると、メンバーの認識にズレが生じやすく、話が行ったり来たりでまとまらない空中戦の会話になってしまいます。
情報が不足していたり、散乱した状態での資料作成は簡単ではありませんが、仮に間違った内容であったとしても資料は作成するべきでしょう。
資料によって情報が可視化されていることで、メンバーの共通認識のベースを作ることができます。また、間違っているところは指摘されるので、今後の認識合わせに繋がります。
もちろん資料作成が難しい議題もあるとは思いますが、資料化できる情報は極力資料化して会議に臨むことが好ましいです。


## 準備がすべて
会議を上手くファシリテートするためには、入念な準備が欠かせません。
今ある情報を整理し、会議の目的とゴールを設定し、それらに基づいた資料を作成するだけでも場合によっては多くの時間を費やすと思います。
それに加えて、会議の一連の流れをシュミレーションし、想定問答等も準備すると尚良いでしょう。
ファシリテーションに慣れるまでは、実際に資料を説明する練習もしておくのがベストです。
準備することはたくさんあり、とても大変な作業です。ただ、会議に参加するメンバーが多ければ多いほどその会議の開催には大きなコストがかかっているということは認識しておかなければなりません。準備不足によって不毛な会議になってしまったら、そのコストを無駄にしてしまうことになるのです。
また、入念な準備をすることで会議で自信を持って話すことに繋がると思います。
不安な状態で話すより、自信を持って話せる状況の方が自分としても嬉しいはずです。
会議の準備をしっかりし、良いファシリテーションにつなげていきましょう！
論文読み：Contextual Instance Decoupling for Robust Multi-Person Pose Estimation

# Contextual Instance Decoupling for Robust Multi-Person Pose Estimation
CVPR 2022 Oral

[元論文](https://openaccess.thecvf.com/content/CVPR2022/papers/Wang_Contextual_Instance_Decoupling_for_Robust_Multi-Person_Pose_Estimation_CVPR_2022_paper.pdf)
[github](https://github.com/kennethwdk/CID)

# Contextual Instance Decoupling for Robust Multi-Person Pose Estimation

## 概要
- CIDは、混雑したシーンでの複数人姿勢推定において、個々の人物を分離し、そのキーポイントを高精度に特定する新しい手法
- 人物のバウンディングボックスに頼らず、画像内の人物を複数のインスタンス認識特徴マップに分離することで、各特徴マップを用いて特定の人物のキーポイントを推定する

:::note info
従来より行われているtop-down手法などの研究がいまだに多いものの、CIDという新しい手法として高い精度を持つ手法を提案した！
:::

## 従来手法との比較
従来の複数人姿勢推定手法は、大きく三つのカテゴリに分類される：
1. **トップダウン法**: バウンディングボックスを検出し、その範囲内でポーズ推定を行う
2. **ボトムアップ法**: すべてのキーポイントを検出し、それを個々の人物にグループ化する
3. **シングルステージ法**: 人物特徴に基づいてキーポイント座標を直接回帰する
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/d57a8c45-ceaf-50fc-b4e0-846a17158116.png)

これらの手法にはそれぞれ以下の課題があった：
- トップダウン法はバウンディングボックスの検出エラーに対して敏感であり、バウンディングボックス外のコンテキスト情報を活用できない
- ボトムアップ法はキーポイントのグループ化が複雑で、キーポイントの位置誤差を修正できない
- シングルステージ法は長距離の回帰が難しいため、精度が低下しやすい

## 新規性
CIDの新規性は、画像内の人物を複数のインスタンス認識特徴マップに分離し、各特徴マップを用いて特定の人物のキーポイントを推定する点にある．これにより、他の人物からの影響を排除し、バウンディングボックスのサイズよりも大きなスケールでコンテキスト情報を探索することが可能になる．

## 提案手法
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/131d987f-b11e-7cde-1e3e-388e7079ffd3.png)

- **インスタンス情報抽出 (IIA) モジュール**: 入力画像から各人物の位置と特徴を抽出し、各人物を表す特徴マップを生成する
- **グローバル特徴分離 (GFD) モジュール**: 各人物の位置と特徴に基づいて、元の特徴マップをインスタンス認識特徴マップに分離する．これにより、各特徴マップは特定の人物のキーポイント推定に使用される
- **対照損失の導入**: 隣接する人物の特徴が類似している場合でも、各人物の特徴を効果的に区別できるように対照損失を導入する

## 結果と評価
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/e60df7df-d031-4d3f-7c59-c0ab37ec407e.png)
良好な結果を残している

:::note info
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2323577/8f489209-d294-f563-655f-0ce916ac5ca6.png)
提案している新規モジュールのGFDの方で、SpatialとChannelそれぞれに特徴を抽出するが、Channelの寄与率が高い
:::

## 結論
CIDは、複数人姿勢推定において、混雑したシーンでの人物の区別を効果的に行い、豊富なコンテキスト情報を活用してキーポイントの位置を推定する新しいパイプラインを提案している．従来の手法と比較して、検出エラーに対するロバスト性が向上し、キーポイントのグループ化や長距離回帰の難しさを軽減することができた．
ITパスポート 表計算（関数）

・関数
ある目的の計算をするために、あらかじめ用意された数式
その数式に、計算に必要な値（引数）を入力すると、計算結果（戻り値）を自動的に算出し、返す

・関数の種類
・合計（A1:A5）
セルA1からセルA5までの範囲に含まれる数値の合計を返す
・平均（A1:A5）
セルA1からセルA5までの範囲に含まれる数値の平均を返す
・最大（A1:A5）
セルA1からセルA5までの範囲に含まれる数値のうちの最大値を返す
・最小（A1:A5）
セルA1からセルA5までの範囲に含まれる数値のうちの最小値を返す
・個数（A1:A5）
セルA1からセルA5までの範囲に含まれるセルのうち、空白セルでないセルの個数を返す
・条件付個数（A1:A5,>25）
セルA1からセルA5までの範囲に含まれるセルのうち、25より大きなセルの個数を返す
・整数部（A1）
セルA1の値以下で最大の整数を返す
例
整数部（3.9）＝3
整数部（-3.9）＝-4
・剰余（A1,A2）
セルA1の値をセルA2の値で割ったときの剰余を返す
・表引き（A3:H11,2,5）
セルA3からセルH11までの範囲の左端（A3）のセルから行と列をそれぞれ1,2,,と数え、行方向に2、列方向に5移動したセルの値（E4）の値を返す
VSCodeのかわいい拡張機能一覧

# はじめに

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

VSCodeのかわいい拡張機能を集めてきたので記事にさせていただきます。

# vscode-vector-aquarium

魚を飼うことができます。

https://marketplace.visualstudio.com/items?itemName=le-nn.vscode-vector-aquarium

![スクリーンショット 2024-07-12 22.41.38.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/f7a1a5dc-24c5-3241-1208-321d200846f9.png)

# QuackTrack Cursor

文字を書くとアヒルがついてきます。

https://marketplace.visualstudio.com/items?itemName=2Guys1Account.quackrack-cursor

![スクリーンショット 2024-07-12 23.13.04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/56d63a0a-a9f2-7c6e-6563-f415d94c7fd0.png)



# nyan-mode

下の方でスクロールすると猫が動きます。

https://marketplace.visualstudio.com/items?itemName=zakudriver.nyan-mode

![スクリーンショット 2024-07-12 22.53.09.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/1197b898-5ba4-138d-f9ba-d61147621c4a.png)

# codachi

動物を飼うことができます。コードを書いていくと経験値が溜まり成長します。

https://marketplace.visualstudio.com/items?itemName=Pegleg.codachi

![スクリーンショット 2024-07-12 23.02.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/a3be5473-b809-e3f3-7205-d7005e4c12e9.png)

![スクリーンショット 2024-07-12 23.02.17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/b5fa1264-ca3c-0174-63a3-652d0363d287.png)

# Tamagotchi Clicker

コードを書いてたまごっちを育てることができます。

https://marketplace.visualstudio.com/items?itemName=Tzanou.tamagotchi

![スクリーンショット 2024-07-12 23.06.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/f179919c-d2ab-d874-3e93-5a0e5daab6a8.png)

# Bongo Cat Buddy

キーボードの入力に合わせて猫が動きます。

https://marketplace.visualstudio.com/items?itemName=JohnHarrison.bongocat-buddy

![スクリーンショット 2024-07-12 22.48.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/009d8226-e7d8-9564-29f5-d402f4c3bfaa.png)

# vscode-pet

ペットを飼うことができます。

https://marketplace.visualstudio.com/items?itemName=tonybaloney.vscode-pets

![スクリーンショット 2024-07-12 22.44.41.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3715123/1ef5d67d-42a0-a296-d506-d45e4b84a6c4.png)


# おわりに

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

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

# 参考

https://zenn.dev/remrem/articles/1927424ef516c5

https://qiita.com/nacho0707/items/aa96ff116e1ade3f28a3
Rust で Welcome to AtCoder を解いてみた

[Qiita Engineer Festa 2024（キータ・エンジニア・フェスタ 2024） - Qiita](https://qiita.com/official-campaigns/engineer-festa/2024)
において、約1ヶ月で38記事という大量の記事の投稿を要求されることがわかった。
そこで、あまりコストをかけずに記事数を稼ぐ方法を考えた結果、「Welcome to AtCoder を様々な言語で解く」ことを思いついた。
単に解くだけでなく、使用する言語仕様の解説を入れれば、記事として一応成立するだろう。

# Welcome to AtCoder

[PracticeA - Welcome to AtCoder](https://atcoder.jp/contests/abs/tasks/practice_1)

Welcome to AtCoder では、以下の形式で整数 $a$, $b$, $c$ および文字列 $s$ が入力として与えられる。

```text
a
b c
s
```

この入力をもとに、与えられた整数の和 $sum = a + b + c$ および文字列 $s$ を、以下の形式で出力することが求められる。

```text
sum s
```

# 今回用いた Rust の機能

## プログラムの枠組みと変数宣言

[Parsing command line arguments - Command Line Applications in Rust](https://rust-cli.github.io/book/tutorial/cli-args.html)

Rust のプログラムは、以下の形で書くことができる。

```rust
fn main() {
    // 処理内容
}
```

`let` を用いることで、変数を宣言して値を割り当てることができる。

```rust
let 変数名 = 値;
```

## 数値の加算

[Add in std::ops - Rust](https://doc.rust-lang.org/std/ops/trait.Add.html)

`+` 演算子を用いることで、数値の加算を行うことができる。

## データの出力

[std::fmt - Rust](https://doc.rust-lang.org/1.39.0/std/fmt/index.html)

`println!` を用いることで、標準出力にデータを出力し、さらに改行を出力できる。
第1引数に書式文字列、第2引数以降にデータを指定し、書式文字列中の `{}` の位置にデータを埋め込んで出力できる。

```rust
println!(書式文字列, データ, ...)
```

## データの入力

[Stdin in std::io - Rust](https://doc.rust-lang.org/std/io/struct.Stdin.html#method.lines)
[BufRead in std::io - Rust](https://doc.rust-lang.org/std/io/trait.BufRead.html#method.lines)

以下のようにすることで、標準入力から1行ずつ読み込むイテレータを得ることができる。

```rust
let mut lines = io::stdin().lines();
```

:::note info
イテレータを用いる際は、`let` だけでなく `mut` もつけないと、値を取得する処理でエラーになるようである。
:::

このイテレータは `Option<Result<String, Error>>` 型のデータを返すので、2回 `unwrap()` を用いることで各行のデータを文字列 (`String`) で得ることができる。
得られる文字列は改行文字を含まないようである。

```rust
let line = lines.next().unwrap().unwrap();
```

この機能は `std::io` モジュールを用いるので、プログラムの先頭で以下のようにしてこのモジュールを取り込む。

```rust
use std::io;
```

## 文字列の数値への変換

[String in std::string - Rust](https://doc.rust-lang.org/std/string/struct.String.html#method.parse)

`文字列.parse().unwrap()` を用いることで、文字列を数値に変換できる。
変換先の型は、代入先の型で指定できる。

```rust
let str = "72";
let value : i32 = str.parse().unwrap();
```

## 文字列の分割

[String in std::string - Rust](https://doc.rust-lang.org/std/string/struct.String.html#method.split_whitespace)

`文字列.split_whitespace()` により、文字列を空白で分割した各部分を得るイテレータを得ることができる。

```rust
let str = "hello world";
let mut parts = str.split_whitespace();
```

このイテレータは `Option<&str>` 型の値を返すので、1回 `unwrap()` を用いることで各部分の文字列を得ることができる。

```rust
let part = parts.next().unwrap();
```

# 提出コード

```rust
use std::io;

fn main() {
    let mut lines = io::stdin().lines();
    let line1 = lines.next().unwrap().unwrap();
    let line2 = lines.next().unwrap().unwrap();
    let line3 = lines.next().unwrap().unwrap();
    let a : i32 = line1.parse().unwrap();
    let mut bc = line2.split_whitespace();
    let b : i32 = bc.next().unwrap().parse().unwrap();
    let c : i32 = bc.next().unwrap().parse().unwrap();
    println!("{} {}", a + b + c, line3);
}
```

[提出 #55491327 - AtCoder Beginners Selection](https://atcoder.jp/contests/abs/submissions/55491327)
AWS ECS上からRailsアプリケーションにBedrock+Claude 3 Haikuを取り込んでみた

## Claude 3 Haikuは安い・美味い・速い

基本的に応答スピードが早く、日本語入出力にも長け、速いのが特徴です。

以下Bedrock経由での価格ですが、Claude 3 Sonnetは他と比較して1/10以下の金額で使えるのが非常に良いです。応

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/293892/9cb13398-28c5-532c-d88b-556845799872.png)

詳細はコチラ

https://aws.amazon.com/jp/bedrock/pricing/


2024年7月時点で、応答速度もSonnetの2倍程度はやく、非常に魅力的です。個人で使ったり、製品のプロトタイプとして活用するには非常に魅力的です。


## AWS Bedrockを使うメリット

- 学習・管理コスト
    - AWSに慣れているエンジニアが弊社には多かった
    - AIだけAzureに外出しせずとも、AWS内ですべて完結出来る
- セキュリティ
    - ECSタスクロールのみで実行出来る為、設定が容易
    - TOKENなどを発行する必要が無い
    - S3上のファイルを呼び出したりも、アクセス権をそこまで気にせず可能
- AWS系のリソースとの相性が良い
    - Lambda+API Gatewayとか、いろいろ使えそう

## とりあえずRails上で試してみる

### 基本モデルのアクセス申請

AWS Bedrockに移動し、基盤モデルを選択。2024年7月現在、日本のリージョン(東京、大阪)では利用不可なので、利用可能なリージョンに変更しましょう。今回は安定のus-east-1を利用しました。

まずはモデルの利用申請をしましょう。
モデルの利用申請をする際に「何に使うの？」とか聞かれると思いました。私の場合「本アカウントのECS上で動いているWEBアプリケーションにて、言語モデルを使った機能開発を行う」としたところ、1分程度で即アクセス権が付与されました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/293892/a86396bf-ffa2-7444-26cc-826c5ffcd0d8.png)

### IAMの変更

ECSのアプリケーションで設定しているタスクロール(タスク実行ロールじゃないよ)に、`AmazonBedrockFullAccess`を紐付けてください。

尚、ReadOnlyの権限では、実行時エラーが起きました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/293892/14a8ef3c-4d99-f2a3-49ef-f966bfc4d238.png)

### Gemfileの設定
Gemfileに以下の一行を追加してください。
```:Gemfile
gem 'aws-sdk-bedrockruntime'
```

やることはそれだけです。とりあえず使うだけであれば、configなどの設定は基本不要です。(やったら便利な場合もあるが、必須ではない)

## 試しにWEB(ECS EXEC)に入ってRailsコンソールから呼び出してみる

コードを実装するのが面倒なので、ECS EXECで環境に入り、コードを直打ちしてみます。

```ruby:サンプルコード
bedrock_client = Aws::BedrockRuntime::Client.new(region: 'us-east-1', credentials: Aws::ECSCredentials.new)

body_hash = {
  "anthropic_version": "bedrock-2023-05-31",
  "max_tokens": 1000,
  "system": "Respond only in Japanese.",
  "messages": [
    { "role": "user", "content": "ポケモンユナイトで勝つ方法を教えて" }
  ]
}

body = body_hash.to_json

response = bedrock_client.invoke_model({
  accept: "application/json",
  content_type: "application/json",
  body: body,
  model_id: "anthropic.claude-3-haiku-20240307-v1:0"
})


answer_hash = JSON.parse(response.body.string)
```

ポイントは、ECSの環境上ではcredentialに`Aws::ECSCredentials.new`を入れることです。手元開発環境の場合は、おとなしく環境変数などに入れたACCESS_KEYなどを使いましょう。手元開発とそれ以外でクレデンシャルの設定を分けておくことをおすすめします。


最終的にanswer_hashの中身はこんな感じになりました。

```ruby
{"id"=>"msg_bdrk_xxxxxxxxxx",
 "type"=>"message",
 "role"=>"assistant",
 "model"=>"claude-3-haiku-20240307",
 "content"=>
  [{"type"=>"text",
    "text"=>
     "ポケモンユナイトで勝つポイントはいくつかありますね。\n\n1. 自分のキャラクターやアイテムを十分に理解し、状況に応じて最適な戦略を立てることが重要です。\n\n2. チームメイトとコミュニケーションを取り、お互いに協力して戦うことが大切です。\n\n3. マップの状況を把握し、重要なエリアを確保するタイミングを逃さないよう気をつける必要があります。\n\n4. アイテムの取得や進化、スキルの使い分けなどを意識して、戦闘力を高めましょう。\n\n5. 相手チームの動きを読み、機会を逃さずにタイミングよく攻撃することも勝利への鍵となります。\n\nこれらのポイントを意識しながら、自分のプレイスタイルに合わせて戦略を立てていくことが重要です。試行錯誤を重ね、慣れていくことで、きっと勝つことができるはずです。頑張ってください!"}],
 "stop_reason"=>"end_turn",
 "stop_sequence"=>nil,
 "usage"=>{"input_tokens"=>33, "output_tokens"=>321}}
```

私の場合、リクエストをClaude3+Bedrockに合わせて生成するのに時間がかかりました。が、そこさえなければ、わずか10分程度でWEBアプリケーションからAIが使えるようになります。

超絶簡単なので、是非皆さん試してみてください。
ラズパイ5でNginxインストール

がっつり使う予定はあまりないので、ほぼ最低限の設定です。

### リポジトリを追加
```
echo "deb http://nginx.org/packages/mainline/debian/ $(lsb_release -cs) nginx" | sudo tee /etc/apt/sources.list.d/nginx.list
```
### Nginxの公開鍵を追加
```
wget http://nginx.org/keys/nginx_signing.key
sudo apt-key add nginx_signing.key
```
### インストール
```
sudo apt install nginx
```

### ドキュメントルートのパーミッション設定
nginxのドキュメントルートがデフォルトで/var/www/htmlになってたの知りませんでした...
(/etc/nginx/sites-available/defaultに記載あり)

sudoでnginxをインストールしたので、ドキュメントルートの所有者がrootになっているが、
HTMLの編集時に毎回root権限必要なのめんどくさいですよね。

https://gakumon.tech/nginx/nginx_permission_main.html

ドキュメントルートの所有権を適当なグループに変更してあげればよいです。
(www-dataに書き込み権限を与えないようにだけ注意)
```
$ group add documenteditor // cat /etc/group 見て使えそうなグループあればそれでもよい
$ sudo usermod -aG documenteditor pi
$ sudo chown -R pi:documenteditor /var/www/html
(drwxr-xr-xになってればOK)
$ sudo chown -R pi:documenteditor /var/www/html/*
$ chmod 664 /var/www/html/*
(-rw-rw-r--になってればOK)
```
ApiGateway から Lambda にパラメータを渡す

# 概要
今更だが、ApiGatewayからLambdaを呼び出した際に、指定したパラメータのみを渡す設定方法をまとめた。
ただし**以下の「Lambda プロキシ統合」の設定はFalseにする前提で進める。**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1909565/c4662705-f02a-acb1-a47c-af1e520379ed.png)


# 設定
1.対象のリソースにて、統合リクエストを選んで「編集」を押下
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1909565/87ac8de9-9ad0-95e1-6333-c45d19b38e45.png)
<br/><br/>
2.リクエストパススルーを推奨の設定のままにし、マッピングテンプレートを記載する
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1909565/9ea6832b-3dc5-6058-0bf2-35c1dc1a35c8.png)
```
"Lambdaに渡すパラメータキー": "$input.params('呼び出し元が渡したパラメータキー')"
```
上記で、指定したパラメータがLambdaに渡される
<br/><br/>
# 注意ポイント
「テンプレートが定義されていない場合」を選び、マッピングテンプレートの「コンテンツタイプ」で指定した「Content-Type」をリクエストheaderで設定しないと、「Unsupported Media Type」と怒られてリクエストがLambdaに到達できないので注意
<br/><br/>
# 参考
https://docs.aws.amazon.com/ja_jp/apigateway/latest/developerguide/integration-passthrough-behaviors.html
Javaで「文字列を正規表現パターンを使って分割する」の動作を確認してみた

# 概要

Javaで「文字列を正規表現パターンを使って分割する」の動作を確認してみました。
以下のページを参考にしました。

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

# 実装

以下のファイルを作成しました。
```JSample20_1.java
class JSample20_1{
  public static void main(String[] args){
    String regex  = ";|:";
    String str = "赤色:青色;黄色:;";

    String[] result = str.split(regex, 0);
    for (int i = 0 ; i < result.length; i++){
      System.out.println("[" + result[i] + "]");
    }

    System.out.println("-- --");

    result = str.split(regex, -1);
    for (int i = 0 ; i < result.length; i++){
      System.out.println("[" + result[i] + "]");
    }

    System.out.println("-- --");

    result = str.split(regex, 2);
    for (int i = 0 ; i < result.length; i++){
      System.out.println("[" + result[i] + "]");
    }
  }
}
```

以下のコマンドを実行しました。
```
$ javac JSample20_1.java 
$ java JSample20_1 
[赤色]
[青色]
[黄色]
-- --
[赤色]
[青色]
[黄色]
[]
[]
-- --
[赤色]
[青色;黄色:;]
```

# まとめ

何かの役に立てばと。
【PHPUnit】PHP のテストファイルを一括で全部実行したい

# はじめに
PHP でテストファイルを複数作って、それを一つずつ実行するのがめんどくさかったので、テストファイルを一括で実行できるクラスのメモ。
IntelliJ で実行する前提なので、実行ファイルはないです。
パスの指定は各々気をつけましょう。

# 継承したクラスのメソッドを全部実行

メソッド実行なのでテスト結果が 1 つにまとめられてしまう。
テストじゃなくて別の使い方とかで応用できそうだなとか思ったり。

```php
<?php

namespace Tests\Controller;

class AllControllerTestExecutor
{
    /**
     * ControllerTestTemplate を継承しているクラスを全て取得し、テストを実行する
     * @return void
     */
    public function testAll(): void
    {
        // ./Api ディレクトリ内の Controller のテストクラスを全て取得する
        $controller_test_classes = $this->getControllerTestClasses();
        foreach ($controller_test_classes as $controller_test_class) {
            // ControllerTestTemplate を継承しているクラスのみテストを実行する
            if (!($controller_test_class instanceof ControllerTestTemplate)) {
                continue;
            }
            // テストを実行する
            $controller_test_class->testAll();
        }
    }

    /**
     * ./Api ディレクトリ内の Controller のテストクラスを全て取得する
     * @return array ./Api ディレクトリ内の Controller のテストクラス
     */
    private function getControllerTestClasses(): array
    {
        $controller_test_classes = [];
        $files = glob(__DIR__ . '/Api/*ControllerTest.php');
        foreach ($files as $file) {
            $class_name = 'Tests\\Controller\\Api\\' . basename($file, '.php');
            $controller_test_classes[] = new $class_name();
        }
        return $controller_test_classes;
    }
}
```

# (おすすめ) フォルダ内にあるテストメソッドを全て実行する

テストメソッドを全て実行するので、それぞれのメソッドごとにテスト結果が出力される。

```php
<?php

namespace Tests\Controller;

use PHPUnit\Framework\TestSuite;

class AllControllerTestSuite
{
    /**
     * ControllerTestTemplate を継承しているクラスを全て取得し、テストを実行する
     * @return TestSuite
     */
    public static function suite(): TestSuite
    {
        $suite = new TestSuite('All Controller Tests');

        $controllerTestClasses = AllControllerTestSuite::getControllerTestClasses();

        foreach ($controllerTestClasses as $controllerTestClass) {
            if (!($controllerTestClass instanceof ControllerTestTemplate)) {
                continue;
            }
            $suite->addTestSuite(get_class($controllerTestClass));
        }

        return $suite;
    }

    /**
     * ./Api ディレクトリ内の Controller のテストクラスを全て取得する
     * @return array ./Api ディレクトリ内の Controller のテストクラス
     */
    private static function getControllerTestClasses(): array
    {
        $controller_test_classes = [];
        $files = glob(__DIR__ . '/Api/*ControllerTest.php');
        foreach ($files as $file) {
            $class_name = 'Tests\\Controller\\Api\\' . basename($file, '.php');
            $controller_test_classes[] = new $class_name();
        }
        return $controller_test_classes;
    }
}
```


# おまけ

コマンドラインでも実行可能。
パスが違ったりすると思うのでそれは頑張ってください (丸投げ)

```bash
/bin/php /var/pj/vendor/phpunit --no-configuration --testsuite "/(Tests\\Controller\\AllControllerTestSuite::suite)( .*)?$/" --test-suffix AllControllerTestSuite.php /var/pj/tests/Controller --teamcity --cache-result-file=/var/pj/.phpunit.result.cache --testdox --verbose
```
zipファイルを破損させて、復元してみる

## はじめに
最近、仕事でzipファイルを扱っていたのですが、ファイルが破損していたためファイルの一部が破損していました。
なにか、zipファイルを復元する方法がないか調べていたら、復元するコマンドを見つけたので今回実践していこうと思います。

## zipファイルを破損させて、復元する
### zipファイルを破損させる
まず、破損させたzipファイルを作成します。
`sample.txt`というファイルを作成します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1328154/aec39f9c-1f8a-5fca-a58d-3effdee7fa08.png)

zipコマンドでファイルをzipに圧縮します。
```sh
 zip sample.zip sample.txt
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1328154/b30f7ebc-83e1-b7eb-bfc2-c0489634e94d.png)

それでは、zipファイルを破損させたいと思います。
zipファイルを破損させる方法は色々ありますが、今回はhexeditコマンドを用いて、バイナリファイルを編集します。
hexeditはファイルを16進数（Hex）の形式で表示し、編集することができます。

以下のコマンドを実行します。
```sh
hexedit sample.zip
```
すると、下のようにバイナリデータを編集することができます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1328154/7c8ef22b-1c7e-2151-42ea-d81406ed9b52.png)

最後の`00 00 00 00 00`を`FF`に置き換えます。(FFと入力すれば置き換わります)
※編集する場所によっては修復不可の場合もあります。今回は大丈夫な部分です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1328154/042bc8c8-8563-ddeb-0508-684fbf42b78c.png)
Ctrl + Xを押して、yでsaveします。

unzipコマンドで`sample.zip`を解凍してみます。
```sh
$ unzip sample.zip
Archive:  sample.zip

caution:  zipfile comment truncated
error [sample.zip]:  missing 4294967040 bytes in zipfile
  (attempting to process anyway)
error: invalid zip file with overlapped components (possible zip bomb)
```
エラーが出て解凍できないことが確認できます。

### zipファイルを復元する
zipコマンドで-FFというオプションを指定してファイルを修復します。
```sh
$ zip -FF sample.zip --out repaired.zip
Fix archive (-FF) - salvage what can
        zip warning: zipfile comment truncated - ignoring
 Found end record (EOCDR) - says expect single disk archive
Scanning for entries...
 copying: sample.txt  (19 bytes)
Central Directory found...
EOCDR found ( 1    167)...
```
実行すると、`repaired.zip`というファイルが作成されます。

`repaired.zip`を解凍してみます。
renameで`repaired_sample.txt`という名前のファイルに解凍します。
```sh
$ unzip repaired.zip
Archive:  repaired.zip

caution:  zipfile comment truncated
replace sample.txt? [y]es, [n]o, [A]ll, [N]one, [r]ename: r
new name: repaired_sample.txt
 extracting: repaired_sample.txt
```

ファイル内容も破損なく、復元されているのが確認できます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1328154/68b5e051-0d5e-d0cc-63ca-f1e3dd976da5.png)

## 終わりに
今回は復元可能な部分を編集し破損させることで、zipファイルを破損状態から復元することができました。
zipファイルが破損してしまっている場合は今回のようにやれば復元できるかもしれません。
WordPressの「更新に失敗しました。 返答が正しい JSON レスポンスではありません。」への対処【更新2024/10/28】

WordPressで下書き保存時に「更新に失敗しました。 返答が正しい JSON レスポンスではありません。」というエラーが出る原因について、よく出るエラーの割には原因が色々っぽいので、自分が当たってしまった原因をメモしておきます。

# 原因1 : and
文中にandという文字列が含まれていることが原因の一つでした。
これはWordPress日本語のサポートフォーラムでも挙げられており（[リンク](https://ja.wordpress.org/support/topic/%E3%83%96%E3%83%AD%E3%83%83%E3%82%AF%E3%82%A8%E3%83%87%E3%82%A3%E3%82%BF%E3%83%BC%E3%81%AEjson%E3%83%AC%E3%82%B9%E3%83%9D%E3%83%B3%E3%82%B9%E3%81%AE%E3%82%A8%E3%83%A9%E3%83%BC/)）投稿によると"**SQLインジェクションからの防御**"に関するものらしく、他にもand、or、true、false、function等が要注意であるようです。
### 対策
対処療法としてはan dのように文字列を千切るか、ａｎｄのように全角にするかなどでしょうか？
ただ本文中に"and"入力不可というのはどう考えてもアレなので他のところに原因がありそうな気がしますが…
[対処されている方はいるようで](https://www.u-ziq.com/blog/2024/01/wordpress-waf.html)、いろいろやりよう自体はあるのかもしれません。

~~苦肉の策として"αnd"にしてみるなど。~~

【追記2024/10/28】
()でも同様のエラーが生じるようです。文字実体参照でも(と)で閉じられた際にエラーが発生します。
全角ではエラーにならないため、全角でも問題ない場合は全角をおすすめします。

# 原因2 : 「メディアとテキスト」機能
これについてはまだ詳しく調べられていないので詳細にどこが原因かわからないのですが、画像にテキストを併記できる「メディアとテキスト」機能でエラーが発生するようです。
設定等どこか触ってしまった部分があるかもしれませんが、コードビュー上では以下のようになっています。(※念のためコード内のid等一部変えています)
```html
<!-- wp:media-text {"align":"center","mediaId":hoge,"mediaType":"image","mediaWidth":36,"verticalAlignment":"top","imageFill":false,"focalPoint":{"x":0.5,"y":0.5}} -->
<div class="wp-block-media-text is-stacked-on-mobile is-vertically-aligned-top" style="grid-template-columns:36% auto"><figure class="wp-block-media-text__media"><img src="https://hoge.jpg" alt="" class="wp-image-hoge size-full"/></figure><div class="wp-block-media-text__content"><!-- wp:paragraph {"align":"left","style":{"typography":{"fontSize":"18px"}}} -->
<p class="has-text-align-left" style="font-size:18px">hogehoge</p>
<!-- /wp:paragraph -->
```
これの
```html
<!-- wp:media-text {"align":"center","mediaId":hoge,"mediaType":"image","mediaWidth":36,"verticalAlignment":"top","imageFill":false,"focalPoint":{"x":0.5,"y":0.5}} -->
```
部分がどうも悪さをしているようですが、、、
### 対策
「メディアとテキスト」機能を使わない、あるいは機能内のどこか設定を変える？


# 原因1の原因【2024/10/28追記】
どうやらブロックエディターで、ブロック内（コードエディター上ではコメントアウトされている部分）に"and"等の文字列を含むとエラーになるようです。
```HTML
<!-- wp:paragraph -->
<p>andが利用不可な場合</p>
<!-- /wp:paragraph -->

<!-- wp:paragraph -->
<p>ブロック内に"and"をいれるとJSONレスポンスエラーが生じる。</p>
<!-- /wp:paragraph -->
```
ひとまず"and"等の単語についてはこれで対処できそうですが、どうも()についてはこれでもなおエラーが生じる場合があります。
これの厄介なポイントは、たとえブロック内でも**場合によっては**エラーにならないなど、挙動が安定しないところ…

# 原因1の原因の原因?【2024/10/28追記】
ありえない見出しですみません。
このエラーは現在WordPressのプラグインの一つである「Custom Post Type UI」で作成した"カスタム投稿タイプ"での固定ページでのみ確認しているため、原因はそこかもしれません。
バージョンは1.15.1です。アップデート次第また挙動を確認します。

***
# 終わりに
とりあえず上２つに対処してエラーは出なくなりました。
根本的な対処ではないのでもう少し調べたいところです。対処法等ご存じの方はコメント等で教えていただけると幸いです…
えっ？Google Colabは使い捨てLinuxじゃないの？

# はじめに
みなさんはGoogle Colaboratory（略称：Google Colab・Colab）を使ったことがありますか？

https://colab.research.google.com/#

Googleアカウントさえあれば、誰でも・いつでもPythonの実行環境を手に入れられる、凄く便利でありがたいサービスです。有料プランもありますが、基本的に無料の状態で困ることはありません。

今回はこのGoogle Colabを使い捨てLinuxとして利用する方法を紹介します！

# 使い捨てLinuxとして使う
実はGoogle Colabでは、Pythonのプログラムだけでなく、Linuxのコマンドも実行することができます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2921137/b397f98d-ea97-ad9b-1659-492a94063774.png)

行の先頭に「!」をつけると、その行はPythonプログラムではなく、Linuxコマンドとして実行されます。

また、ディレクトリの移動をしたい場合は、「!」ではなく「%」を使います。

ちなみに中身はUbuntuです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2921137/44ba0387-1d75-ef1a-f259-473cc4224772.png)

# 気を付けないといけないこと
これこそが**使い捨てLinux**と呼んでいる理由です。

Colab ノートブックに保存できるのは、コードやテキストが書かれたセルのみで、Googleのサーバー側で動かしているランタイム、つまりLinuxの状態は保持できません。

つまり、ランタイムが切断された時点で、Linuxで作業していた内容はすべて吹き飛びます。

作業した結果を保持したい場合は、「GoogleドライブをGoogle Colabに接続し、そこに出力するようプログラムを書く」か、「左側のタブから手動でダウンロードする」必要があります。

# Colab Proだとターミナルが使えるらしい
ちなみに、有料プランであるColab Proに登録すると、わざわざ「!」や「%」を使わなくとも、ターミナルを使ってLinuxを操作できるそうです。

# おわりに
「自前のLinux環境に影響を与えたくないけど、あるプログラムを動かしたい！」というようなシチュエーションで活用できるかと思います。

wgetやaptのようなコマンドも利用できるので、活用法は無限大です。ぜひ試してみてください！

最後までお読みいただきありがとうございました！
【参加レポート】Amazon Bedrock Prototyping Camp に行ってみた

# はじめに

先日「Amazon Bedrock Prototyping Camp」に参加してきましたので、そのレポートです。

# きっかけ

現在弊社ではキャリア支援サービスの「ミートキャリア」を手掛けています。
今後このキャリア支援サービスで培ったノウハウやデータを活用して、その人に合ったキャリアやマッチする求人を提案するようなサービスを開発しようとしています。

https://www.nikkei.com/article/DGXZQOUC25BB20V20C24A6000000/

この開発においてユーザーや求人のデータを分析してマッチングする機能で生成AIが活用できないかと考えました。

ちょうど「Amazon Bedrock Prototyping Camp」という1日かけてAWS上で生成系AIのプロトタイプの実装までを行うイベントがあるとAWSの方に教えてもらいました。
実際に触ってみるのが一番理解も早いし、生成AIに関する知識がない初心者でもOKとのことだったので参加することにしました。

# イベント参加まで

事前に対応する必要があったのは、事前アンケート（生成AIでどのようなことをしたいか、どのようなデータを使うか等）への回答と作成したプロトタイプの検証で使用するデータを用意するだけでした。
AWSの設定は当日のハンズオンで行うとのことだったので、その他特に準備するものはありませんでした。

# イベント当日

イベントの会場はAWSの目黒アルコタワーのオフィスです。（ほぼ目黒雅叙園？）
受付を済ませて会場に入るとスクリーンに会社ごとの席順が表示されていました。
自分は単独での参加でしたが（自分一人しかエンジニアがいない）、2〜4名くらいで参加している会社が多かったと思います。
年齢層は20代〜40代くらいまで幅広く女性も多かったので、昨今の生成AIへの関心の高さを感じました。

## イベントの流れ

今回のイベントの大まかな流れとしては、午前中に生成AIの基礎知識の座学と Amazon Bedrock の導入設定を行い、 ランチ休憩を挟んで午後からは各自でプロトタイピングを作成していくというものでした。

午前中の座学では、生成AIの基礎知識や Amazon Bedrock の概要、生成AIのモデルの作成方法などを学びました。 また、生成AIのプロダクトへの導入事例やユースケースの考え方などビジネスよりの話などもありエンジニア視点以外のものも学べました。

個別の質問は特に時間を設けてはいなかったのですが、質問用のスプレッドシートが用意されておりそこに記入することで、 リアルタイムにAWSのサポートメンバーの方が回答してくれるため気軽に質問できて良かったと思います。

今回自分が特に印象に残っていることが、「生成AIの場合深く考えるよりもすぐに検証した方が早いことが多い」というものでした。
生成AIのモデルの検証においては実際にデータを使って検証しないとわからないことが多く、プロンプトやRAGのデータチューニング、そしてユーザーからのフィードバックで精度をあげていくので検証を繰り返すことが重要だと感じました。

:::note
これらの内容はgithubに公開されているので実際にプロダクトに導入する際にも参考にしようと思います。
https://github.com/aws-samples/aws-ml-enablement-workshop
:::

## ランチ休憩

ランチ休憩ではグリルチキンのトマトソースのおしゃれなお弁当が用意されていました。
また、お菓子や飲み物も自由に取れるようになっていて、ランチタイムはリラックスして過ごすことができました。

## プロトタイピングの作成

午後からは、実際に生成AIのプロトタイプを作成していきます。
この時間はAWS のサポートメンバーの方が各グループで ビジネス面・技術面のディスカッションやアドバイスをしてくれました。

システム構成を考えているところで、以前からオンラインのMTGなどでやりとりをしているAWSのソリューションアーキテクトの方とお会いできたので、システム構成やプロンプトなどのチューニングについてディスカッションをしました。ホワイトボードを使って説明してもらったり、実際にデータやコードを見てもらったりすることもできたので、これはオフラインでのイベントの良さでもあるなと思いました。

ちなみに今回プロトタイプで作ろうとしたものの構成図は以下のようになります。
生成AIを使ったプロダクトというともっと複雑なものを想像してしまうかもしれませんが、Bedrockまわりも含め わりとシンプルなものになったと思います。

プロトタイプ構成図
![figure01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3760785/0f61a8d6-8872-167b-93c2-4f59b488712e.png)


# 所感

これまで生成AIに関する知識はあまりなかったのですが、このイベントに参加して生成AIの基礎知識を学ぶことができ、 また実際にAWSのサービス（Amazon Bedrock）を使って プロトタイピングを作って動かすところまで1日でできたのでとても有意義でした。
実際に触ってみることで理解が深まり、なんとなくとっつきにくかった生成AIに対するハードルが下がったと感じました。

また、AWSのサポートメンバーの方々が親切で、質問にも丁寧に答えてくれるので初心者でも安心して参加できるイベントだと感じました。
今後生成AIへの需要はますます高まっていくはずなので、 興味がある方は是非このようなイベントに参加してみるのが良いかなと思います。
C_TS422_2021 SAP Certified Application Associate SAP S/4HANA Production Planning and Manufacturing対策（63/100）

【63日目】
トピック 7：SAPS/4HANAにおける拡張計画（9/14）

≪問題63≫
モード選択はSAPS/4HANAのアドバンスト計画で利用できるスケジュールオプションの1つです。どのようなときにモード選択を利用できますか。
□複数の作業が1つの製品に対して設定されているとき
□複数の計画手配が1つのリソースに存在するとき
□複数の製品バージョンが1つの製品に対して設定されているとき
□1つの作業内で代替リソースが使用されているとき

≪解答≫
□複数の作業が1つの製品に対して設定されているとき
□複数の計画手配が1つのリソースに存在するとき
□複数の製品バージョンが1つの製品に対して設定されているとき
■1つの作業内で代替リソースが使用されているとき

≪解説≫
◆ 活動の実行に必要なリソースと能力所要量は、モードによって決定されます。日程計画に関連する主要リソースに加えて、1つ以上の副リソースをモードに入力することができますが、能力所要量は計画時に副リソースに対しても登録されます。
◆ 1つの活動に対して複数のモードを割り当てることができます。つまり、活動を処理するための複数の代替リソース（リソースのセット）を割り当てることができます。計画中、利用可能能力を考慮して、最遅時刻に開始されるモードが自動的に選択されます。
◆ PP/DSの詳細計画では特定の優先モードを使用することができます。このために、モードに異なる優先度を割り当て、詳細計画方針で日程計画を実行するモードの優先度を定義することができます。
【備忘】FediverseのWebhook送信先と公開範囲

忘れる度検索してるので覚書。

動作環境：Python 3.12.3

# Webhook送信先(エンドポイント)

## mastodon

マストドンベースインスタンスはこれ（Fedibird等）
```
https://[インスタンスURL]/api/v1/statuses

例:
https://mstdn.jp/api/v1/statuses
```


## Misskey
```
https://[インスタンスURL]/api/notes/create

例:
https://misskey.io/api/notes/create
```

<!--調べたら追記する

## Bluesky
```


例:
https://api.blueskyweb.xyz/v1/statuses
```

-->


# 公開範囲 (visibility)

|  |公開|ホーム(未収載)|フォロワー|DM(※)|
|:-:|:-:|:-:|:-:|:-:|
|**mastodon**|public|unlisted|private|direct|
|**Misskey**|public|home|followers|specified|
<!--調べたら追記する
|**Bluesky**|||||
-->

※DMの場合送信先ユーザの指定が必要
（一応指定しなくても自分にだけ見える投稿は可能）
 
記述は下記参照


## mastodon

`@user_id_1`,`@user_id_2`…：送信先ID
```Python
payload = {
    "status": "@user_id_1 @user_id_2 投稿テキスト",  # メンション付きの投稿テキスト
    "visibility": "direct"  # DMの場合は "direct" を指定
}

```

`status`の`user_id`,`text`を変数にしたもの。
```Python
user_id_1 = "user_id_1"
user_id_2 = "user_id_2"
text = "ここに投稿テキストを入力"

payload = {
    "status": f"@{user_id_1} @{user_id_2} {text}",  # メンション付きの投稿テキスト
    "visibility": "direct"  # DMの場合は "direct" を指定
}
```


## Misskey

`user_id_1`,`user_id_2`…：送信先ID
```Python
payload = {
    "text": "投稿テキスト",
    "visibility": "specified",
    "visibleUserIds": ["user_id_1", "user_id_2"] #DMの場合ユーザを指定
}
```


# リクエストヘッダー

HTTPリクエストヘッダー。
mastodon、Misskey共通

`fediverse_access_token`：各インスタンスで取得したAPIアクセストークン

```Python
fediverse_headers  = {
    "Content-Type": "application/json",
    "Authorization": f"Bearer {fediverse_access_token}"
}
```


# おわり

mastodonとMisskeyで投稿パラメータが違うところでよく引っかかる。
（mastodonは`status`、Misskeyは`text`）
そのうちBlueskyのAPIもやってみたいね
# SQL Serverのデータベースが複数ある構成で、リストアを(半)自動化した話



## はじめに
月次バッチの開発やテストをしているときに、データベースのリストアをしながら開発をしていたのですが、GUI操作でリストアしていくと運用しているデータベースが複数あればあるほど、手間がかかっていました。
その時に、これらを半自動化まで出来るようにしたので、備忘録的に残しておきます。
> ※今回のバックアップファイルは、完全バックアップを想定しています。

### 環境
- SQL Server 2019
- Windows 10

### 処理イメージ

1. リストアするデータベースのリストをTXTファイルから読み取る
2. テキストを元にSQLを生成して、ファイルに出力する
3. SQLファイルをSQL Serverに接続して実行する

> 結構やってることはシンプルで、リストア用のSQLを生成して一括で実行するだけです。

## Management Studioでリストアする方法

- このスクリプトを実行すると、データベースの復元に使用されるSQLが生成される。 

> 自分が使用していたリストア時のオプション
> - ソース     ：☑デバイス ⇒ ローカルのバックアップファイル（完全バックアップ）
> - サーバー接続：☑接続先データベースへの既存の接続を閉じる

```sql
ALTER DATABASE [DBNAME] SET SINGLE_USER WITH ROLLBACK IMMEDIATE;
RESTORE DATABASE [DBNAME] FROM  DISK = N'D:\BKFolder\DBNAME_bk.bak' WITH  FILE = 1,  NOUNLOAD,  STATS = 5;
ALTER DATABASE [DBNAME] SET MULTI_USER;
```
- このSQLを実行すると、データベースがリストアされる。

### ALTER DATABASEのオプション
- SET SINGLE_USER 
    - ユーザー接続を1つに制限する。
    - 他のユーザーがデータベースに接続していると、データベースに対する接続は警告なく切断される。
- WITH ROLLBACK IMMEDIATE
    - トランザクションをロールバックして、他のユーザーの接続を切断する。
- SET MULTI_USER
  - データベースに接続するための権限を持つ、すべてのユーザーが許可する。

### RESTORE DATABASEのオプション
- FROM DISK  
    - バックアップファイルのパスを指定する。
- WITH FILE = 1
  - バックアップファイルセットの最初のリストを指定する。
  - バックアップファイルが複数ある場合に使用する。
- NOUNLOAD
  - RESTORE 操作の後、テープ ドライブにテープを読み込んだままにすることを指定する。
- STATS = 5
  - バックアップ操作の進行状況を示すメッセージを表示する。
  - 今回の場合、5% ごとにメッセージを表示するということだが、あまり正確ではないらしい。。。

## SQL自動生成用
なにわともあれ、ソースということで

```powershell
  #各変数の値は環境に合わせて適宜設定
  $backup_list = "backupfiles.txt"
  $bakpath = "D:\BackupData"
  $outfile = "output.sql"

  # バックアップリストを読み込む
  $bakfiles = Get-Content $backup_list

  foreach ($bakfile in $bakfiles) {
    # BAKファイル名からDB名を取得
    $backup_file = Split-Path $bakfile -Leaf
    $dbname = $backup_file.split("_")[0]

      # バックアップを復元するスクリプトを出力
      $sb = New-Object System.Text.StringBuilder
      
	[void]$sb.AppendLine("ALTER DATABASE $dbname SET SINGLE_USER WITH ROLLBACK IMMEDIATE;")
	[void]$sb.AppendLine("RESTORE DATABASE $dbname FROM DISK='$bakpath\$backup_file' WITH RECOVERY;")
	[void]$sb.AppendLine("ALTER DATABASE $dbname SET MULTI_USER;")

      # 結果をファイルに追記出力
      Write-Output $sb.ToString() | Out-File -Append $outfile
  }

  # SQL Serverに接続してリストアを実行
  $serverName = "サーバー名 or アドレス"
  $userName = "サーバーのユーザー名"
  $userPassword = "サーバーのパスワード"
  sqlcmd -S $serverName -U $userName -P $userPassword -i $outfile
```

### ちょろっと解説
そんなに処理自体は複雑ではないので解説ということでもないですが、
前提として、バックアップファイルのリストをテキストファイルに記載しておく必要があります。
このソースでは、以下のようなファイルを想定しています。

- backupfiles.txt
```txt
dbName1_20110123.bak
dbName2_20110123.bak
dbName3_20110123.bak
…
```
- 書きながら思ったのですがBAKファイルを読み込むところで、  
  色々工夫すれば特定のデータベースのみリストア出来たりすると思います。 


::: note warn
実行する際に、実行ポリシーに引っかかることがあるかもしれませんが  
その場合は以下のようにして実行してください。

```cmd
PowerShell -ExecutionPolicy RemoteSigned .\restore.ps1
```

こうすることで、実行ポリシーを一時的に変更して実行することが出来ます。
:::

## おわりに
今回は、SQL Serverのリストアの自動化について書いてみましたが、同じような要領でバックアップの取得も出来ると思います。
それこそ、バックアップ時に　`backupfils.txt` にバックアップファイル名を追記していけば、バックアップ⇒リストアという流れを自動化することが出来ると思いますので、お試しください。
StableDiffusionをDiscord botで動かす

# はじめに
StableDiffusionをDiscordbotで動かせるようにしてみました。StableDiffusion WebUIはAPIで動かせるようになっているのでそれを使っています。
# Discordサーバー
操作したいパラメータごとにチャンネルを立てます。![スクリーンショット 2024-07-13 0.55.17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3680953/1b7cfcec-c3d2-53fa-2476-d213c369eccd.png)
これ以外に実行コマンドを送るのと、完成したものを貼るチャンネルを立てます(自環境ではrunにしている)。
# bot
https://github.com/akimax74/SDbot

トークンはpython-dotenvで保存しています。
パラメーターのチャンネルに値を送ると、txt2imgの実行用のjsonファイルが更新されます。
それを実行用チャンネルに適当にメッセージを送ると生成開始され完成したらそのチャンネルに画像を貼るようになっています。
![スクリーンショット 2024-07-13 1.07.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3680953/4efe904f-2007-e2d6-a15c-a736592f956b.png)
生成された画像はbase64で返ってくるので、デコードして保存しそれをチャンネルへ送信するようにしています。
また、prompt,sampler,checkpointのチャンネルでは"?"(promptは"!lora")と送ると使えるオプションが返ってきます。![スクリーンショット 2024-07-13 1.04.26.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3680953/0ed6a394-7c3c-6985-eb62-98b5090e450a.png)

# 参考資料

https://qiita.com/1ntegrale9/items/cb285053f2fa5d0cccdf

https://qiita.com/Morio/items/7538a939cc441367070d

https://qiita.com/chatrate/items/aa6625f6663fa2ca33d6

https://note.com/el_el_san/n/n34e7ceecc9f4
【PMP】PM・PL未経験の合格記と勉強方法

## 概要
2024/05に受験し合格し1発合格したので、勉強方法などを共有します。
・勉強時間：60時間程度
・勉強期間: 3ヶ月（2024/03～2024/05）

## 自己紹介
年齢:27歳
経験:PG/SE 6年(PM・PL経験なし)

## 背景
システムエンジニアからのキャリアアップとして、
プロジェクトマネージャー・プロジェクトリーダーをするため受験しました。
IPAのプロジェクトマネージャー試験ではなくPMPを選んだ理由は、年3回まで受験可能であるためです。
年1回の試験だと、不合格の場合、1年間試験のための知識を維持しなければならないのがデメリットだと感じました。

## PMP試験
PMP（Project Management Professional）試験は、プロジェクトマネジメントにおける国際的に認知された資格試験であり、PMI（Project Management Institute）が提供しています。
この資格は、プロジェクトマネージャーとしてのスキルと知識を証明するものとして広く認識されています。
## 試験の形式と内容
試験形式: コンピュータ
試験時間: 230分
出題数: 180問（うち5問は試験にはカウントされない）
出題形式: 選択問題（多肢選択、ドラッグ＆ドロップなど）
## 試験要件
### 学歴
#### 学士号またはそれ以上の学位を持つ場合
・プロジェクトマネジメントにおける36ヶ月の実務経験
・35時間以上のプロジェクトマネジメント教育またはCAPM®（Certified Associate in Project Management）認定
#### 高校卒業、または同等の学歴を持つ場合
・プロジェクトマネジメントにおける60ヶ月の実務経験
・35時間以上のプロジェクトマネジメント教育またはCAPM®（Certified Associate in Project Management）認定

## 費用
合計 : 95,669円
| 名前       | 金額	          | 備考       |
|------------|----------------|------------|
| 教科書 | 4,378円   | 1冊 |
| 問題集 | 9,395円 | PMI Study Hall(49USD) + Udemy(1,800円) |
| 35時間研修 | 1,600円 | Udemy |
| 受験料+PMI会員入会費 | 80301円(516USD) | 受験料(364USD)、PMI会員入会費(152USD) ※受験料は10%クーポンを使用 |

10%クーポンはCouseraの「Google Project Management Professional Certificate」を修了した際に発行されました。
## 試験準備
### 35時間の公式研修を受講する(必須)
私はUdemyの以下の研修を受講しました。
[PMP Certification Exam Prep Course 35 PDU Contact Hours/PDU](https://www.udemy.com/share/101WOC3@Qv3nwd5Qw1DAmYKeSIXnQQ7Rwk-ztWFGKZyi3D5zvNctrI3zJLKBsyLpANclr3U2/ "PMP Certification Exam Prep Course 35 PDU Contact Hours/PDU")

## 受験申請手続き
PM・PL経験がないので申請が通るか不安だったが、プロジェクトマネジメントについて貢献した部分を記載して問題なく受理されました。
以下のブログを参考にしました。
[【PMP】受験申請手続きの流れ | 準備～申請完了までの全工程](https://hashimoto-marine.com/pmp-app/ "【PMP】受験申請手続きの流れ")

## 使用した教材（教科書）
| 名前       | 金額	          | 
|------------|----------------|
| PMP完全攻略テキスト PMBOKガイド第7版対応 | 4,378円   |

内容を一通り読んで、理解度テストと模擬試験を1回解きました。

## 使用した教材（問題集）
| 名前       | 金額	          | 問題数	          | 
|------------|----------------|----------------|
| PMI Study Hall ESSENTIALS | 7,595円 |360問|
| PMP (Project Management Professional) 試験模擬問題集 全360問(2回分) | 1,800円 |360問|

試験模擬問題集はUdemyのセール時に購入しました。

## 勉強方法
教科書を読んだ後に問題集をたくさん解きました。
間違えた箇所をPMBOKやアジャイル実務ガイドで参照すると良いと思います。
問題を解くだけでも合格できますが、より余裕を持って合格を目指すことができます。

通勤中にはYouTubeでプロジェクトマネジメントの動画を見ていました。
特にビギナーシリーズがプロジェクトマネジメントを理解するのに役立ちました。
[I LOVE PM / プロジェクトマネジメント専門チャンネル / イトーダ](https://youtube.com/@ilovepm?si=0qDhfbKuOz6RAEv7 "プロジェクトマネジメント専門チャンネル")

## 試験
### 試験中
全180問あり、60問ごとに10分の休憩が取れます。休憩中は部屋の外に出て水分補給などができます。試験時間は1時間程度残りました。
### 試験内容
試験では全く同じ問題はほぼ出ませんので、模擬試験で回答の傾向を掴むことが重要です。
計算問題は1問程度でしたので、無理して勉強する必要はありません。
### 試験後
試験の結果は2日後にメールが届きました。合格ラインは60%でしたが、65%で合格しました。思っていたよりギリギリでした。
## まとめ
英語での受験申請や勉強方法を決めるのが難しい試験でしたが、試験自体はシチュエーション問題がメインなので、そこまで難しいとは感じませんでした。
PM・PL経験がなくても合格することができたので、今後目指していく方でも挑戦できる試験です。
(しくみ)SSD1306の配置順にx,yを出力して遊ぶ


目的
SSD1306の内部のRAMの配置に沿ってXとyを出力して
ROM等から読み出してダイレクトに出力する

●SSD130は、ページと言う構造を持っている

1ページは、128バイトで構成されている

図

![o_coq207.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/5bafd802-cf8a-57c9-e7df-4ff7f32e1a4f.jpeg)

●SSD1306の全体構成

構成は、128バイトのページが8ページある

図

![o_coq206.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/60064805-27de-c536-001e-dbda9256fa94.jpeg)

● x,yの出力順


```c++


for (int ii = 0; ii < 8192; ii++) {

    //SSD1306のバッファーの配置順のxとyを求める
    y = ((ii & 0b0001110000000000 ) >> 7) + ( ii & 0b0111);
    x =  (ii & 0b0000001111111000) >> 3;

いろいろな処理

}//for ii


```




おまけ

```c++


//データの配列の定義
uint8_t databytes[2] = {DATA_MODE, 0x00};
int jjkk = 0;
int qq = 0;

//ドットを打つ
void Dot(int x, int y, int c) {

  qq = qq >> 1;
  qq = qq | ( c << 7);

  jjkk++;

  if ( jjkk >= 8 ) {

    databytes[1] = qq;
    write_s(databytes, 2);

    qq = 0;
    jjkk = 0;
  }//end if

}//DOt


```


https://qiita.com/caa45040/items/e322de00db644bfb4c01
ChatGPTは「54字の物語」を書けない

# はじめに
みなさんは「54字の物語」を知っていますか…？

氏田雄介さんが考案した短編小説のフォーマット、また、その形式の小説のことを指します。

PHP研究所から本も出版されています。

https://www.php.co.jp/54ji/

たった54字しかないのにも関わらず、それはもう綺麗な伏線回収があり、非常に面白いです。

先ほどお風呂に入っていたところ、唐突に「ChatGPTは54字の物語を書けるのだろうか」と疑問に思ったので、実際に試してみました。

# 検証

| 検証日 | 2024/07/12 |
|:-:|:-:|
| 検証環境 | ChatGPT Web版 |
| モデル | GPT-4o |
| カスタム指示 | なし |
| パーソナライズ | オフ |

以上のような環境で検証を行いました。

## 1回戦
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2921137/412ac18b-c657-3471-7c2e-8ff7f5931664.png)
予想はついていましたが、全然面白くないです。
さらに、出力された小説は54字になっていません。

続けてプロンプトを送信してみます。

## 2回戦
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2921137/add250bc-5554-21bd-d79e-3474a7b7ef14.png)
ほとんど変わりませんでした。
ですが正直ここまでは想定内です。

さらにプロンプトを送信しました。

## 3回戦
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2921137/8251644e-fb90-f2cc-d136-f144625670bf.png)
ChatGPTが「文字数」についてどういう認識をしているのか確認したところ、Pythonコードを作成し、文字数を計算し始めました。

計算結果を表示した後、条件に従っていなかったことを認識し、再度小説を生成しました。

しかし、再度生成されたものも文字数は54字になりませんでした。残念。

# おわりに
## 意外だったこと
「文字数のカウント・その値の出力」を頼んだだけなはずなのに、条件に適していないことを認識して、再度生成を始めたところです。

結局正しい文字数になっているものはありませんでしたが、誤りを自ら発見し動作するというのは、かなり凄いことだと思っています。

## 結果
**（今のところ）ChatGPTは「54字の物語」を書けない。**

私が与えたプロンプトが悪い可能性もありますが、まだChatGPTは「文字数」を上手く処理できないようです。

54字の物語はChatGPTの画面ではなく、氏田さんによる完成度の高いお話を本で読むべきでしょう。

プロンプト等、何か良い案がありましたら、コメントで教えて頂けると幸いです。
最後までお付き合いいただきありがとうございました。
開発効率向上！Makefileでリントと型チェックを簡単実行

## 背景
リントの度に `npx eslint --fix 'src/**/*.{js,jsx,ts,tsx}` など入力するのが面倒なので、 Makefile にまとめた

## やったこと
- 必要なコマンドを Makefile にまとめる
- 利用するコマンドを `make help` に追加

```
# ヘルプ
.PHONY: help
help:
	@ echo '  lint-all		# リントと型チェックを含めた全ての検証を実行（自動修正は除く）'
	@ echo '  lint-fix		# 全てのリントエラーを自動修正'

# リント全て実行（自動修正は除く）
.PHONY: lint-all
lint-all: lint type-check

# リントを実行
.PHONY: lint
lint:
	npm run lint

# 型チェックを実行
.PHONY: type-check
type-check:
	npm run type-check

# リント自動修正を実行
.PHONY: lint-fix
lint-fix: eslint-fix lint-format
	@echo "Fix lint completed successfully!"

# リントと自動修正を実行
.PHONY: eslint-fix
eslint-fix:
	npx eslint --fix 'src/**/*.{js,jsx,ts,tsx}'

# コードのフォーマットを実行
.PHONY: lint-format
lint-format:
	npm run format

```

## 感想
`make lint-fix && make lint-all` するだけなので簡単
FSCalendarの表示が崩れる問題への対処療法

iOSのアプリでカレンダーを実装するとき、FSCalendarを利用しております。
大変便利です。ありがとうございます。

https://github.com/WenchaoD/FSCalendar

ある日アプリを開いたところ表示が崩れておりました... あれ？


![IMG_3862.jpeg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3812996/0b2dbe77-ee50-2fc8-8f3f-310691b9b448.jpeg)
（こうなるはずが、）

![IMG_3861.jpeg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3812996/4ba3d50c-b614-9916-e9fc-fe64bc9f5257.jpeg)
（こんななってた）

なんやこの崩れ方は...

---

# 調査

いろいろ調べましたところ、
端末によって出る、出ないがあることがわかりました。

さらに、このFSCalendarを配置しているViewの横サイズをわずが0.001ポイントずらしただけで正常表示していた端末が異常表示になって
また別の端末ではその逆の現象が起こりました。

さらにさらに、Viewの横サイズではなく、横の配置位置（ｘ）をずらしただけでも同じような状況の変化がありました。

ここまでで、横サイズの小数点計算絡みのバグかなーと思いました。

---

そして、Githubのissueで探したところ、下記の情報が見つかりました。

https://github.com/WenchaoD/FSCalendar/issues/1415

iOS 17 doesn't renders the months correctly
とのことで、
ここに書かれている崩れ方とは違いますが、まあ似たようなことが起こっているのと
サイズの小数点が問題に起因しているようにも感じました

---

# 対処療法

他人のswiftパッケージの中身を修正してしまうのは手段としては有りますが、
メンテナンス性が悪いので、最終手段としてとっておき、
今回はパッケージの外から表示が崩れないようにコントロールする方針にしました。


storyboardで、ViewをSafeAreaのセンタリング、サイズを90%に設定していました。

これだと、iPhone SE3の端末では、x = 19.5ポイントの位置に配置しておりました。

とりあえずの対処療法としては、小数点が生じないようにすることが重要と考え、


ViewをSafeAreaのセンタリング、サイズを100% - 定数値N  ...のような設定に変更しました。
これによって、xの値もwの値も、いずれも整数値となります。

-> これで、小数点が発生せず、FSCalendarの内部の計算も小数点誤差がなくなり、
崩れずに表示できるのでは？と考えました。

---

動作確認として、
手持ちのiOS端末５種類でFSCalendarを表示したところ
すべての端末でカレンダーの表示崩れが発生しなくなりました。

FSCalendarの表示崩れに困っている方がいらっしゃいましたら、
配置位置とサイズを整数にすれば解決するかもしれません。