OmniAICreator/Qiita-1.07M huggingface dataset:
OpenFOAM9のデータ出力のタイミング

# データ出力のタイミングが古いバージョンと違う

OpenFOAM9では，出力のタイミングが変わりました。

具体例をいうと，0.1sのデータを出力して，それ以降5秒おきにデータ出そうとすると前なら
5.1
10.1
15.1
と0.1sから5秒おきに出てました。

OpenFOAM9だと
5
10
15
と出るようになりました。

リリースにちゃんとかいてありました。　https://openfoam.org/release/9/

> Data Output: When a case is stopped and restarted, results are now written to subsequent time directories referenced to the original start time of the case rather than the restart time [ commit 7aca9b ].

すっきりした。

# 問題は
これはこれで良かったんですが，adjustableRunTime使ってて問題が出ました。OpenFOAM9なのに
5.1, 10.1, 15.1とデータが出ることが発生しました。

OpenFOAM9では，beginTimeとstartTimeがあって，この2つをつかって，データ出力のタイミングをコントロールしています。

beginTimeは各時刻のデータのディレクトリのなかのuniform/timeにあります。普通これが0になっています。これだとリスタートしても，時刻0s基準で，データが出力されます。

今回問題がおきた計算では，0.1sのbeginTimeがなぜか0.1になっていました。なので，0.1sから5秒おきにデータが出力されたようです。

# まとめ
OpenFOAM9より前のバージョンと同じように，データ出力の時刻を設定したいときは，uniform/timeのbeginTimeを調整すれば，可能です。

（自分でbeginTimeを変更した覚えがないのに，なんで変わったのか。。。）

# 補足
ちなみにwriteIntervalを時間帯によって変えられるようにもなったみたいです。

> Time: The setTimeStep function object allows the user to configure a writeInterval which changes over time [ commit bae95b ].

https://github.com/OpenFOAM/OpenFOAM-dev/commit/bae95b1291c14fbc408a6f5533028ee8ab61f527
暗号資産業界でライターをしています｜現在、Crypto Timesで仕事中！

暗号資産の世界に魅せられたライターとして、日々この業界の進化を追いかけています。複雑な技術や最新のトレンドを分かりやすく伝えることをモットーに、記事や解説を執筆しています。暗号資産が持つ可能性を信じ、その魅力を多くの人に伝えたいと思っています。

この業界は常に変化し続けており、新しいプロジェクトや技術が次々と生まれています。私は常にアンテナを張り巡らせ、正確な情報を分かりやすく伝えることで、読者の皆様が暗号資産の世界をより深く理解できるよう努めています。

暗号資産は単なる投資対象ではなく、私たちの未来を大きく変える可能性を秘めています。私はこの革新的な技術を応援し、その発展に貢献できるよう、ライターとして精進していきます。

暗号資産に興味がある方は、ぜひお気軽にご連絡ください。一緒にこのエキサイティングな世界を探索しましょう！
 

 

現在仕事をしている会社：Crypto Times　https://crypto-times.jp/

私が実際に執筆した記事一覧：https://crypto-times.jp/user/crypto-troll/
【Puppeteer】awaitのどこかの処理でTimeoutになる??

## Puppeteerの処理にてtimeoutエラーが発生

async関数内にて定義されているawaitのどこかしらの処理が完了しておらず、timeoutになるエラーが発生。

## とりあえずawaitが定義されている箇所にログを置く

awaitが定義されている箇所の後ろに`console.log`にてログを置いてみた。

## await browser.close();の箇所が原因

`await browser.close();`の後ろに置いたログが出力されずにtimeoutになった。

# 【解決方法】

 `await Promise.race([browser.close(), browser.close(), browser.close()])`
 上記に変更することで正常にawaitの処理を完了することができた。



 参考記事
 https://github.com/puppeteer/puppeteer/issues/2485
GitLab CI で reviewdog を活用する方法

# はじめに

こんにちは、Gakken LEAP のバックエンドエンジニアの mizuno です。
以前に[GitLabのartifacts reportsを設定する](https://qiita.com/GleapPost/items/5df3ee2ce9c727a16b19) で codequality を実装しました。
codequality を使い始めたのですが、実行時間が少し長いため、Rubocop と Brakeman を別々に分けて同時に実行し、速度を上げたいと思いました。
また、[reviewdog](https://github.com/reviewdog/reviewdog) を使って GitLab のマージリクエストにコメントを追加できることが分かったので、こちらも実装してみました。

## reviewdog の下準備

### APIトークンの発行

reviewdogを導入するにあたり、APIトークンが必要になるため、
[個人アクセストークンの作成](https://gitlab-docs.creationline.com/ee/user/profile/personal_access_tokens.html#%E5%80%8B%E4%BA%BA%E3%82%A2%E3%82%AF%E3%82%BB%E3%82%B9%E3%83%88%E3%83%BC%E3%82%AF%E3%83%B3%E3%81%AE%E4%BD%9C%E6%88%90)、[プロジェクトアクセストークンの作成](https://gitlab-docs.creationline.com/ee/user/project/settings/project_access_tokens.html#%E3%83%97%E3%83%AD%E3%82%B8%E3%82%A7%E3%82%AF%E3%83%88%E3%82%A2%E3%82%AF%E3%82%BB%E3%82%B9%E3%83%88%E3%83%BC%E3%82%AF%E3%83%B3%E3%81%AE%E4%BD%9C%E6%88%90)を参考にしつつ、どちらかでAPIアクセストークンを発行しトークンを控えます。
プロジェクトの環境変数に`REVIEWDOG_GITLAB_API_TOKEN`というキー名にして、発行したトークンを登録します。

## reviewdogのインストール

共通して、`before_script` でreviewdogの[インストール](https://raw.githubusercontent.com/reviewdog/reviewdog/master/install.sh)とgitをインストールします。

### Rubocopの例

```yaml:rubocop.gitlab-ci.yml
rubocop:
  image: registry.gitlab.com/pipeline-components/rubocop:latest
  stage: test
  variables:
    GIT_STRATEGY: clone
    GIT_DEPTH: 0
  before_script:
    - wget -O - -q https://raw.githubusercontent.com/reviewdog/reviewdog/master/install.sh | sh -s
    - apk add git
  script:
   - rubocop | bin/reviewdog -f=rubocop -reporter=gitlab-mr-discussion
```

### Brakemanの例

[action-brakeman](https://github.com/reviewdog/action-brakeman/blob/master/script.sh#L57-L65)の `script.sh` を参考にし、`script`に実装しました。

```yaml:brakeman.gitlab-ci.yml
brakeman:
  image: ruby:3.3-alpine
  stage: test
  variables:
    GIT_STRATEGY: clone
    GIT_DEPTH: 0
  before_script:
    - wget -O - -q https://raw.githubusercontent.com/reviewdog/reviewdog/master/install.sh | sh -s
    - apk add git
    - gem install brakeman
  script:
    - brakeman --quiet --format tabs | bin/reviewdog -f=brakeman -reporter=gitlab-mr-discussion
```

:::note warn
brakmanのimageにgitをインストールできなかったため、`ruby:3.3-alpine`で代用しています。
:::

## 動作確認

### Rubocop

* 省略記法の検知

![Rubocop](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3712998/58e63241-6062-13c7-68b8-6f2fc9e7f9e9.png)

### Brakeman

* SQLインジェクションの検知

![Brakeman](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3712998/fbe39250-279e-b258-bee6-f45577b753f3.png)

## まとめ

同時にjobが実行され高速になり、またマージリクエストの変更画面でも修正箇所が分かりやすくなり便利になりました。
`reviewdog -list`で使用可能なフォーマットは確認できるので、対応しているフォーマットがある場合はぜひ使ってみて下さい。

Gakken LEAP では教育をアップデートしていきたいエンジニアを絶賛大募集しています！！

<https://gakken-leap.co.jp/recruit/>

## 参考記事

<https://qiita.com/yokoo-an209/items/b1071c716cfe937b2210>
【JavaScript】クラスの継承

# 継承とは
>クラスの継承は、あるクラスが別のクラスを拡張するための方法です。
つまり、既存の機能の上に、新たな機能を作ることができます。


# 継承前
```ドラえもんクラス.js
class Doraemon {
    constructor() {
        this.name = 'ドラえもん';
    }

    walk() {
        alert(`${this.name}は歩く`);
    }
}


const doraemon = new Doraemon();
doraemon.walk(); // ドラえもんは歩く
```

```ドラみクラス.js
class Dorami {
    constructor() {
        this.name = 'ドラみ';
    }

    walk() {
        alert(`${this.name}は歩く`);
        alert('気分が良くなる');
    }
}

const dorami = new Dorami();
dorami.walk(); // ドラみは歩く 気分が良くなる
```

# 継承していく
### 1. ロボットクラスを作成し、共通部分を抜き出す
```ロボットクラス.js
class Robot {
    constructor() {
        this.name = 'ロボット';
    }

    walk() {
        alert(`${this.name}は歩く`);
    }
}

const robot = new Robot();
robot.walk(); //　ロボットは歩く
```

### 2. ロボットクラスを `extends` する
```ドラえもんクラス.js
class Doraemon extends Robot {}

const doraemon = new Doraemon();
doraemon.walk(); // ロボットは歩く
```
`extends`することで、`Doraemon`クラスのオブジェクトは`Robot`クラスのメソッドが利用できるようになります。そのため、上記のように`Doraemon`クラスが空でも親の`walk()`メソッドを利用できます。

しかし、今のままでは`doraemon.walk()`を実行しても、「ロボットは歩く」と表示されてしまいます。

### 3. コンストラクタのオーバーライド
コンストラクタの`this.name`を「ドラえもん」に変更したい場合は、コンストラクタをオーバーライドします。

コンストラクタのオーバーライドをすることで、継承したクラスを初期化する時に子クラスに特化した処理を行うことできます。
`super`を使用して、親クラスの初期化処理を子クラスに継承させつつ、子クラス独自の初期化処理を追加します。
```ドラえもんクラス.js
class Doraemon extends Robot {
    constructor() {
        super(); // 親クラスのコンストラクタを呼び出す
        this.name = 'ドラえもん'; // ドラえもん独自のプロパティ
    }
}

const doraemon = new Doraemon();
doraemon.walk(); // ドラえもんは歩く
```

これで「ドラえもんは歩く」と表示されるようになりました。

### 4. メソッドのオーバーライド
次に、ドラみクラスについてですが、ドラみは歩くと気分が良くなります。
そのため、`walk()`メソッドをオーバーライドする必要があります。

デフォルトでは親クラスからメソッドを取得しますが、子クラスで同名のメソッドを指定すると、子クラスのメソッドが呼び出されるようになります。

オーバーライドする際は、親メソッドを完全に置き換えるのではなく、拡張や微修正を加えることが望ましいとされています。
そのため、子メソッドに追加した処理の前後、または処理中に親メソッドを呼び出します。
親メソッドは`super.method(...)`で呼び出せます。

```ドラみクラス.js
class Dorami extends Robot {
      constructor() {
        super();
        this.name = 'ドラみ';
    }
    
    feelBetter() {
        alert('気分が良くなる');
    }
    
    walk() {
        super.walk(); // Robotクラスのwalk()の呼び出し
        this.feelBetter();
    }
}


const dorami = new Dorami();
dorami.walk(); // ドラみは歩く 気分が良くなる
```

# 継承後
```ロボットクラス.js
class Robot {
    constructor() {
        this.name = 'ロボット'
    }

    walk() {
        alert(`${this.name}は歩く`);
    }
}
```

```ドラえもんクラス.js
class Doraemon extends Robot {
    constructor() {
        super();
        this.name = 'ドラえもん';
    }
}

const doraemon = new Doraemon();
doraemon.walk(); // ドラえもんは歩く
```

```ドラみクラス.js
class Dorami extends Robot {
    constructor() {
        super();
        this.name = 'ドラみ';
    }
    
    feelBetter() {
        alert('気分が良くなる');
    }
    
    walk() {
        super.walk();
        this.feelBetter();
    }
}

const dorami = new Dorami();
dorami.walk(); // ドラみは歩く 気分が良くなる
```

# 参考
- [クラスの継承](https://ja.javascript.info/class-inheritance)
Bashスクリプトによるファイル編集と自動生成

## はじめに
Bashは強力で柔軟なシェルスクリプト言語で、テキスト処理、ファイル操作、システム管理タスクなど、多岐にわたる用途に適しています。
今回、Bashのスクリプトを用いたファイル編集と自動生成の例を紹介します。

## 内容
Pelicanブログのテンプレート部分の編集を事例にあげます。
```text
template="Title:
Date:
Category: Blog
Tags:
Slug:
Authors: stpete
Summary:
```
Title, Date, Tags, Slug, Summary に決められた情報をbash scriptで書き込んで行きます。


## 実行結果例
先に実行結果を示すと、bash scriptを実行することで、以下のように個々の項目が正しく編集されたファイルを生成します。

生成ファイル名称: 2024-06-27_101.md
生成ファイル内容:
```text
Title: Stop the war. スペイン語
Date: 2024-06-27
Category: Blog
Tags: war, スペイン語
Slug: 101
Authors: stpete
Summary: Stop the war.
```

## bash script(create.sh)の内容
```bash
#!/bin/bash

# 日付を取得
current_date=$(date +%Y-%m-%d)

# ファイル通番の範囲の指定
start=101
end=104

# 編集内容を定義
langs=("スペイン語" "イタリア語" "フランス語" "ドイツ語")
texts=("Stop the war.")
kws=("war")

# テンプレート内容
template="Title:
Date:
Category: Blog
Tags:
Slug:
Authors: stpete
Summary:
"

# 指定範囲の数字に対してファイルを作成または編集
for number in $(seq $start $end); do
    # 数字をゼロ埋め（zfill(3)）する
    zfilled_number=$(printf "%03d" $number)
    
    # ファイル名を作成
    file_name="${current_date}-${zfilled_number}.md"
    
    # 言語のインデックスを計算
    lang_index=$((number - start))

    # 要素を取得（配列が1つの要素しか持たない場合は常に最初の要素を使用）
    current_lang="${langs[$lang_index]}"
    current_text="${texts[0]}"
    current_kw="${kws[0]}"

    # ファイルが存在しない場合、テンプレートを追加
    if [ ! -f "$file_name" ]; then
        echo "$template" > "$file_name"
    fi
    
    # 一時ファイルを作成
    tmp_file=$(mktemp)

    # ファイルの内容を読み込み、指定された行を置き換える
    while IFS= read -r line; do
        case "$line" in
            "Date:")
                echo "Date: ${current_date}" >> "$tmp_file"
                ;;
            "Slug:")
                echo "Slug: ${zfilled_number}" >> "$tmp_file"
                ;;
            "Tags:")
                echo "Tags: ${current_kw}, ${current_lang}" >> "$tmp_file"
                ;;
            "Title:")
                echo "Title: ${current_text} ${current_lang}" >> "$tmp_file"
                ;;
            "Summary:")
                echo "Summary: ${current_text}" >> "$tmp_file"
                ;;
            *)
                echo "$line" >> "$tmp_file"
                ;;
        esac
    done < "$file_name"

    # 一時ファイルの内容を元のファイルに書き戻す
    if ! mv "$tmp_file" "$file_name"; then
        echo "エラー: ファイル '${file_name}' の更新に失敗しました。" >&2
        rm -f "$tmp_file"
        exit 1
    fi

    # 確認メッセージ
    echo "ファイル '${file_name}' が作成または編集されました。"
done
```
IFS は "Internal Field Separator" の略です。
IFS= と設定することで、一時的にIFSを空に設定した上で、read コマンドにより行全体を1つの単位として読み込み保持します。

## 実行方法
```bash
bash create.sh
```

## 終わりに

上記のスクリプトはbashの各種機能を含んでいますので、適宜書き換えることで、いろいろな場面に応用可能かと思います。
横からスライドするモーダルの作り方

クリックすると、横からスライドして表示されるモーダルの作り方です。
![画面収録 2024-05-20 13.41.19.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1578726/ab82a762-ffef-bae9-18bd-a106acbb359d.gif)


# 作り方🍳
#### 1. ボタンとモーダルの`div`を置く
```sample.html
<button>Click!</button>
<div class="slide-modal"></div>
```
#### 2. `slide-modal`クラスにCSSを当てていく
1. `position:fixed;`を指定して、スライドモーダルをどの位置に表示するか指定する
2. 特定のクラスが付与されたときにスライドモーダルを表示するために、`slide-modal`クラスに`show`クラスがついた時のスタイルを用意する（クラス名はなんでも良い）
3. `show`クラスには`display: block;`と`overflow: hidden;`を指定する
```sample.scss
.slide-modal {
  position: fixed;
  top: 0;
  right: 0;
  width: 500px;
  height: 500px;

  &.show {
    display: block;
    overflow: hidden;
  }
}
```

お好みでスライドモーダルの出し入れの速さを調整したり、重なり順を調整したりする。
```sample.scss
.slide-modal {
  position: fixed;
  top: 0;
  right: 0;
  width: 500px;
  height: 500px;
  background-color: #90CAF9;
  transform: translateX(100%) translateY(0px) translateZ(0px);
  transition: transform 0.2s cubic-bezier(0.23, 1, 0.32, 1);

  &.show {
    display: block;
    overflow: hidden;
    transform: translateX(0%) translateY(0px) translateZ(0px);
    transition: transform 0.2s cubic-bezier(0.23, 1, 0.32, 1);
  }
}
```

#### 3. JSで`show`クラスの付け外しを行う
HTMLにJS用のクラスを付与する。
```sample.html
<button class="js-click-showSlideModal">Click!</button>
<div class="slide-modal js-target-slideModal"></div>
```

JSファイルに処理を追加する。
```sample.js
document
  .querySelector(".js-click-showSlideModal")
  .addEventListener("click", function () {
    const slideModal = document.querySelector(".js-target-slideModal");
    
    if (slideModal.classList.contains("show")) {
        slideModal.classList.remove("show");
    } else {
        slideModal.classList.add("show");
    }
  });
```

### 4. 完成！
<p class="codepen" data-height="300" data-default-tab="result" data-slug-hash="vYwNXvX" data-pen-title="Untitled" data-user="kidorina" style="height: 300px; box-sizing: border-box; display: flex; align-items: center; justify-content: center; border: 2px solid; margin: 1em 0; padding: 1em;">
  <span>See the Pen <a href="https://codepen.io/kidorina/pen/vYwNXvX">
  Untitled</a> by kidorina (<a href="https://codepen.io/kidorina">@kidorina</a>)
  on <a href="https://codepen.io">CodePen</a>.</span>
</p>
<script async src="https://cpwebassets.codepen.io/assets/embed/ei.js"></script>
[T-DASH] テスト自動化で任意のページにある対象要素を探す

# Outline

検索、リスティングページで、探したい要素が任意のpageにあるとする。
任意というのは、テストの実行毎にことなるpageに表示されるという意味である。
この場合、テスト自動化では、固定ページの要素を見つけるという処理では、テストは成功するときもあれば、失敗するときもある。
このため、要素が見つかるまでページ送りを考えたくなる。


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/bdc18d3a-ccef-e8ed-446c-e1125f171f71.png)

今回、この実装の考え方、実装に関して解説する

https://service.valtes.co.jp/t-dash/

# テスト対象

qbookの記事一覧から、一つの記事をさがしだし、クリックする
アクセスしたページに該当記事がなかったら、ページャーの”次”ボタンをクリックする
これを一定回数繰り返す（上限を設定するのは、数百ページとかある場合、もし記事が存在しない時に、数百ページのページング処理を繰り返すため、失敗するまでのテスト時間がかかってしまうからである。）

https://www.qbook.jp/

# 技術的な情報

robot frameworkの
- FOR-END文でループする
- Exist For Loop IF 文で条件を満たしたら（対象の要素が見つかったら）ループを抜ける
- Run Keyword And Return Status 文で、条件文（要素が存在するか）の結果を取り出します。この時、Falseになってもテストは継続します


```
FOR  ${i}  IN RANGE  10
     ${IS_ELEMENT_EXISTANCE} =  Run Keyword And Return Status  XXXXX
     Exit For Loop IF ${IS_ELEMENT_EXISTANCE}
     yyyyy
END
```



# T-DASH

## カスタム動作

以下設定内容を Pager.yamlのファイル名で保存する

```
ACT-CAT-CUSTOM-f7057005-3f12-4487-a156-cf06ae8d61e3:
  action_category_name: Pager
  icon: ''
  color: '#e21628'
  custom_data:
    file_name: Pager
    pip_list: []
    library_list: []
  actions:
    ACT-CUSTOM-aadb1f56-1bbe-48f0-9bd6-dfba00166de5:
      action_name: 見つかるまで次のページをクリックする
      action_type: operation
      action_format: 「画面名」「要素名」が見つかるまで次のページをクリックする
      action_note: ''
      action_args:
      - screen
      - element
      action_def:
      - - FOR
        - ${i}
        - IN RANGE
        - '10'
      - - ''
        - ${IS_ELEMENT_EXISTANCE} =
        - Run Keyword And Return Status
        - Page Should Contain Element
        - ${location}
      - - ''
        - Exit For Loop IF
        - '''${IS_ELEMENT_EXISTANCE}''==''True'''
      - - ''
        - Click Element
        - xpath=//a[@class="pagination__link pagination__link--next minimalbox"]
      - - END
      - - Click Element
        - ${location}
```

次に、作成された Pager.yamlをT-DASHの動作定義 -> カスタム動作 -> カスタム動作をインポート にてインポートし、実際にインポートされた設定内容を開く

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/559006d2-aaf0-62f8-513e-cc3f9ebb1e3f.png)

4行目の10はページング処理の上限を定義します。
7行目のxpathはpagerのXPathです。developertoolなどでページ送りをする要素のXPathを取得してここに記載します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/e031aa08-c826-783a-00c1-0e480ab7464d.png)

## テストケース

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/c3bd2498-4a5f-b4b4-bb70-203f08f7225c.png)

３行目が、記事一覧の１ページ目から、「負荷テストとは？」の記事を探す処理である。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/55f0354e-1a86-04bb-0c14-e9c5ee713e3d.png)


## テスト実行

実行して、詳細のレポートが下図である。
for loopの0~3回目では、「負荷テストとは？」の要素がみつからないため（false）pagerをクリックします
4回目では、「負荷テストとは？」の要素が見つかったため、For loopからexitします

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/3ed2fec5-cca8-4e19-b501-acfdbb4e45fe.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/267085/a74fb407-71a2-2743-ae86-dcd4cf4084cb.png)
Macで使えるランチャーツール Raycast の便利機能集

# Raycast とは

https://www.raycast.com/

Macで使えるランチャーツールです。
ちょうど、

- クリップボード履歴・スニペット機能の [Clipy](https://clipy-app.com/)
- ウィンドウ制御の [Spectacle](https://www.spectacleapp.com/)
- アプリランチャーの [Snap](https://apps.apple.com/jp/app/snap/id418073146)
- Mac標準の検索機能 Spotlight

をすべて兼ね備えたようなアプリになっています。

ざっくり以下のことができます。

- ホットキーでアプリを起動
- ウィンドウ制御
- クリップボード履歴
- スニペット機能
- アプリ・ファイル検索
- 電卓
- ...etc

その中でも私がよく使っていて便利だと思った機能を紹介します。

# ホットキーでアプリ起動

![ダウンロード.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/408546/68409af8-ed4a-7f81-83a2-551c94546b6b.gif)

[Snap](https://apps.apple.com/jp/app/snap/id418073146) でできることと変わりませんが、M1チップになってから Snap が不調で使えなかったのでめちゃくちゃ助かりました。

`⌥A`で Arc を表示・非表示、`⌥C` で VSCode を表示・非表示など、任意のキーの組み合わせで任意のアプリの表示・非表示ができます。

これでキーボードからいちいち手を離さずにアプリの切り替えが可能になり、開発効率がめちゃくちゃ上がります。

# ウィンドウ制御
![ダウンロード (1).gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/408546/868c7a92-2c85-fc47-9a52-ece07c8bc2e9.gif)

[Spectacle](https://www.spectacleapp.com/) とできることは同じです。

私は Spectacle に合わせて、`⌥⌘F`で画面最大化、`⌥⌘→`で右寄せなどを割り当てていますが、アプリのホットキーと同じく、好きなキーの組み合わせを設定できます。


# クリップボード履歴
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/408546/041a5ae3-c6a3-7845-f071-d0c2e94ebeff.png)

[Clipy](https://clipy-app.com/) と基本的には同じですが、最大の違いは**画像の履歴も保持できる**ことです。

スクリーンショットを複数枚撮って Slack などに投稿したいとき、普通は

- 保存先をクリップボードにして1枚撮って貼り付け、次の1枚を撮って貼り付け…
- 保存先をどこかのフォルダにしてファイルとして保存してアップロード

のどちらかだと思います。

前者は往復が面倒ですし、後者はスクリーンショットを Slack で送ったらもう不要とかだと、いらないファイルが溜まって嫌だったりしますよね。

そんなとき Raycast のクリップボード履歴なら、保存先をクリップボードにして複数枚撮影した後、Slack に複数枚貼り付けとかができて便利です。

# スニペット機能

これも [Clipy](https://clipy-app.com/) にもありますが、Raycast の方がカスタマイズ性は高いです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/408546/bb5dc738-2dd4-026b-4e4e-f33b0abc53ce.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/408546/b3993116-cf08-4cac-0d58-2db42a1bae7f.png)

例えば上のように「日付」というスニペットを用意すると、今日の日付がスニペットとして用意できます。

これを応用すると、ある一文の特定の場所だけ今日の日付を入れたいというスニペットを以下のように作成できます。

```
add -r {date format="yyyy/MM"} 2310EA129 001 100
→ add -r 2024/06 2310EA129 001 100
```

# nits: Quicklink 特定のリンクを瞬時にブラウザで開く機能

少々ニッチですが、個人的にとても便利な機能です。

私の使い方としては、**毎日入る Zoom のリンクを登録する**です。

![Untitled.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/408546/ba363a06-23da-9f9f-6fd9-e1c44bcbd677.png)

**Quicklink** に登録してそれをお気に入りに登録しておくと、

1. Raycast を開く(私の場合は`Shift + Space`)
1. `Enter`

と、キーボード操作だけで Zoom のリンクを開けます。

私の開発チームでは毎日 Zoom で朝会やモブプロ・ペアプロを行っています。
このとき毎回特定の Zoom のリンクを開く必要があるわけですが、通常は

1. リンクがメモしてあるアプリを開く
1. リンクがメモしてある場所を開く(メモやブラウザのお気に入りなど)
1. リンクをクリックする

という動線になり、すばやく Zoom に入りたいときなどなかなか面倒だったので、この機能は嬉しかったです。

# おわりに

Raycast はその他にも多くの機能があり、正直私は全然使い切れていないほどです。
これからも色々試していきたいと思います。
AWS Certified Solutions Architect - Associateを受験した時の話

# はじめに

　自分がSAAの認定資格を取得するまでにCLFとDVAは取得していました。この業界に転職して4年ちょっとになりますが、2024年4月に基本情報を取得し、成長を続けるエンジニアです。
　AWSの実務経験は、弊社に転職して初めて利用し、半年の経験があります。そんな私がSAAを受験し、無事に合格することができました(2024年6月)。合格体験記として少し書いてみようと思います。

# AWS認定 SAAについて

　AWS Certified Solutions Architest - Assosiate（SAA-C03）は、クラウド環境でのアーキテクチャ設計に関する知識とスキルを評価する資格です。この試験は、AWSのサービスを利用して耐障害性が高く、コスト効率の良い、スケーラブルなシステムを設計する能力を証明するものです。
 　試験範囲には、AWSのサービス、セキュリティ、ネットワーク技術、アーキテクチャのベストプラクティスなどが含まれます。実務経験を通じて得た知識をもとに、より高度な設計や最適化が求められるため、幅広い知識が必要とされます。

https://aws.amazon.com/jp/certification/certified-solutions-architect-associate/


# 勉強したこと

　学習手段としては、弊社で教育予算を使って利用しているCloudLicense になります。各試験の最新の要件に即したWeb問題集がいくつかのまとまりとなっており、自分のペースで隙間時間でも学習が進めやすい仕組みです。
　学習時間は限られていましたが、効率よく進めることができたと思います。正答率も正直合格ラインに届いていなかったものの、粘り強く取り組みました。

 https://cloud-license.com/


# 合格はしたが

　会社には5月末～6月頭の受験予定を伝えていたため、良い緊張感をもって受験に臨むことができました。その結果、DVA同様合格ラインにギリギリではあったものの、SAAに合格することができました。
 　SAAに関して、CloudLicenseでの学習を効率良く行えた為、合格することができましたが、資格取得の学習に留まらず、実務を通じて知識を深めていきたいと思います。
　次に受験予定としているAWS Certified Solutions Architect - Professional（SAP）については、CloudLicenseはもちろん、他の教材も利用してしっかりと勉強し、万全の準備で臨みます。

 https://aws.amazon.com/jp/certification/certified-solutions-architect-professional/
React19のformアクション機能の魅力

## はじめに
React19では、新たに`<form action={非同期関数}>`の形式で、フォームアクションが追加されました
これにより、フォームの送信時に非同期関数を直接呼び出せるようになり、よりシンプルなコードが書けるようになります
本記事では、この新機能の使い方とその利便性について詳しく解説します
また、この新機能`useFormStatus`というフォームの送信中の状態を取得するフックも追加されてより利便性が向上しました

## formアクションの使用
以下の例では、フォーム送信時に`handleSubmit`関数が非同期に呼び出されます

### React19の実装例
```jsx
import { useState } from 'react';
import { useFormStatus } from 'react-dom';

async function handleSubmit(formData) {
  const response = await fetch('/api/submit', {
    method: 'POST',
    body: formData
  });

  if (!response) {
    throw new Error('Network response was not ok');
  }
  
  return await response.json();
}

function MyForm() {
  const [status, setStatus] = useState(null);
  const { isPending } = useFormStatus();

  return (
    <form action={handleSubmit} >
      <input type="text" name="name" />
      <button type="submit" disabled={isPending}>
        {isPending ? 'Submitting...' : 'Submit'}
      </button>
      {status && <p>{status}</p>}
    </form>
  );
}

export default MyForm;
```

### この実装の利点
- 簡潔なコード
    - フォームの`action`属性に非同期関数を直接指定することで、コードが簡潔になり、読みやすさが向上します
- 非同期処理の簡素化
    - フォーム送信時に非同期処理を簡単に組み込むことができ、従来のイベントハンドラを使う方法よりも直感的です
- 進行中状態の明示化
    - `useFormStatus`フックを使用することで、フォーム送信中の状態を`isPending`プロパティとして取得し、ボタンの状態を動的に変更できます


## Reat18以前の実装方法
React18以前では、フォームの送信イベントをキャッチし、その中で非同期処理を行なっていました

### React18以前の実装例

```jsx
import { useState } from 'react';

async function handleSubmit(event) {
  event.preventDefault();
  const formData = new FormData(event.target);
  const response = await fetch('/api/submit', {
    method: 'POST',
    body: formData,
  });

  if (!response.ok) {
    throw new Error('Network response was not ok');
  }

  const result = await response.json();

  return result;
}

function MyForm() {
  const [status, setStatus] = useState(null);
  const [isPending, setIsPending] = useState(false);

  const handleFormSubmit = async (event) => {
    event.preventDefault();
    setIsPending(true);

    try {
      const result = await handleSubmit(event);
      setStatus(`Success: ${result.message}`);
    } catch (error) {
      setStatus(`Error: ${error.message}`);
    } finally {
     setIsPending(false);
    }
};

  return (
    <form onSubmit={handleFormSubmit}>
      <input type="text" name="name" />
      <button type="submit" disabled={isPending}>
          {isPending ? 'Submitting... : 'Submit'}
      </button>
      {status && <p>{status}</p>}
    </form>
  );
}
```
React18以前では汎用的な`useState`を多用するのでどうしても分岐が多くなってしまいますね

## まとめ
React19のformアクション機能により、フォームの非同期処理がより簡単かつ直感的に実装できるようになりました
この新機能と`useFormStatus`フックを活用することで状態管理が簡潔で可読性の高いコードを書けるようになり、開発者の負担を軽減することができるようになるでしょう

## 参考リンク

https://ja.react.dev/reference/react-dom/components/form

https://zenn.dev/uhyo/books/react-19-new/viewer/form-action
AstroNvimの導入方法

自分に合ったIDEを1から作成してみませんか？全ての開発環境を1つにまとめられると便利だと思う．本記事ではAstroNvimの環境構築をまとめる．

# AstroNvimとは
[AstroNvim](https://astronvim.com/)とは，[Nvim](https://neovim.io/)を手軽に使うための設定集で，初期状態で拡張機能が揃っているため，インストールするだけでVimの環境が整う．

# AstroNvimのインストール方法
**Macの場合**
```bash
git clone --depth 1 https://github.com/AstroNvim/template ~/.config/nvim
rm -rf ~/.config/nvim/.git
```
インストールが終わったら，以下のコマンドを実行する．
```bash
nvim
```

**Windowsの場合**
```powershell
git clone --depth 1 https://github.com/AstroNvim/template $env:LOCALAPPDATA\nvim
Remove-Item $env:LOCALAPPDATA\nvim\.git -Recurse -Force
```
インストールが終わったら，以下のコマンドを実行する．
```bash
nvim
```

すると，以下の画面になる．

![スクリーンショット 2024-06-27 13.06.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3757442/1d08fab3-4c9b-88dd-b808-adcd224a5de6.png)

# Nerd Fontsをインストール
アイコン表示を有効にするために，以下のコマンドを実行する．
**Macの場合**
````bash
brew install font-hack-nerd-font 
export TERM=xterm-256color
````

# 基本設定のカスタマイズ
`~/.config/nvim/lua/user`
に設定ファイルを作成し，個人の設定を反映する．

設定ファイルのおすすめは以下の記事から．
[鋭意製作中]

# tmuxについて
AstroNvimとtmuxは必須だと思う．ぜひ入れることをお勧めする．
tmuxはターミナルを分割したり，ウィンドウを複数持つことができる．
```bash
brew install tmux
```

以下の記事で詳しく説明する．
[鋭意製作中]

# `おまけ`Vim操作
| キー      | 実行内容       |
|-----------|----------------|
| h | 左へ1つ移動
| j | 下へ1つ移動
| k | 上へ1つ移動
| l | 右へ1つ移動
| i | 挿入モードへ
| o | 新しい行を追加し挿入モードへ
| yy | カーソル位置の行コピー
| dd | カーソル位置の行削除
| v | ビジュアルモードへ
| y | ビジュアルモードで選択した範囲をコピー
| d | ビジュアルモードで選択した範囲を削除
| p | ペースト
| ESC| コマンドモードに戻る

ここからはAstroNvim固有の操作を記載する
| キー      | 実行内容          |
|-----------|----------------|
| Space | Leader key, コマンドの最初に使用する
| Space + w |  内容を保存
| Space + q | 終了
| Space + o | フォーカスの変更
| [ or ] + b| バッファの移動
| space + c | バッファの削除
| H | ドットファイルの表示/非表示
Salesforce開発者を雇う vs Salesforceコンサルタントを雇う

はじめに
Salesforceを効果的に導入し活用するためには、Salesforce開発者とSalesforceコンサルタントの両方の専門知識が求められます。それぞれの役割と利点を理解することで、どちらを雇うべきかが明確になります。
[Salesforce開発者を雇う](https://newwave-solutions.co.jp/hire-salesforce-developers/)
Salesforce開発者は、Salesforceプラットフォームのカスタマイズや拡張を担当します。ApexやVisualforce、Lightning Componentsを使用して、特定のビジネスニーズに合わせたアプリケーションを開発します。
主な役割
カスタムアプリケーション開発: 企業のニーズに応じたアプリケーションの作成。
データベース管理: Salesforceデータモデルの設計と管理。
API統合: 他のシステムとSalesforceの統合。
技術サポート: バグ修正や技術問題の解決。
雇うメリット
高度なカスタマイズが可能。
技術的な問題に迅速に対応。
継続的なシステム改善。
[Salesforceコンサルタントを雇う](https://newwave-solutions.co.jp/hire-salesforce-consultant/)
Salesforceコンサルタントは、Salesforceの導入と最適化に関するアドバイスとサポートを提供します。ビジネスプロセスの分析、設定、カスタマイズ、ユーザー教育を行います。
主な役割
ビジネス分析: 企業のプロセスを分析し、Salesforceの活用法を提案。
設定とカスタマイズ: Salesforceの設定と必要なカスタマイズ。
ユーザー教育: Salesforceの使い方に関するトレーニング。
プロジェクト管理: 導入プロジェクトの計画と管理。
雇うメリット
ビジネスプロセスに精通し、最大限の活用法を提案。
導入プロジェクトの成功率向上。
従業員が迅速にシステムに適応できるよう支援。
結論
Salesforce開発者は技術的なカスタマイズとサポートが必要な場合に最適です。一方、Salesforceコンサルタントはビジネスプロセスの最適化や導入プロジェクトの管理が必要な場合に最適です。企業の具体的なニーズに応じて、適切な専門家を選ぶことが成功の鍵となります。
エンタープライズソフトウェア開発とソフトウェア製品開発

はじめに
現代のビジネス環境では、ソフトウェアの役割はますます重要になっています。特にエンタープライズソフトウェア開発とソフトウェア製品開発は、多くの企業にとって成功の鍵となる要素です。この記事では、これら二つの開発プロセスについて簡潔に説明し、それぞれの利点と課題を考察します。
エンタープライズソフトウェア開発とは
[エンタープライズソフトウェア開発](https://newwave-solutions.co.jp/enterprise-software-development/)は、企業全体で使用されるソフトウェアを設計、開発、および展開するプロセスを指します。これには、CRMシステム、ERPシステムなどが含まれます。
利点
カスタマイズ可能性: 企業の特定のニーズに合わせたカスタマイズが可能。
スケーラビリティ: 大規模なデータとユーザーを処理可能。
統合性: 既存のシステムと容易に統合。
課題
高コスト: 開発と維持に多大な費用がかかる。
時間のかかる導入: 導入には時間がかかる。
ユーザー教育: トレーニングが必要。
ソフトウェア製品開発とは
[ソフトウェア製品開発](https://newwave-solutions.co.jp/software-product-development/)は、市場向けに汎用的なソフトウェア製品を設計、開発、および販売するプロセスです。
利点
広範な市場: 大規模な収益が見込める。
反復的改善: ユーザーフィードバックを元に改良可能。
ブランド認知度: 成功すればブランド力強化。
課題
競争: 市場での差別化が難しい。
顧客サポート: 高品質のサポートが必要。
市場調査とマーケティング: 徹底した調査が必要。
結論
エンタープライズソフトウェア開発とソフトウェア製品開発は、それぞれ異なるニーズと課題を持つ重要な分野です。企業がどちらのアプローチを採用するかは、ビジネスの目標やリソースに依存します。成功には慎重な計画と実行が不可欠です。
Salesforce開発会社とSalesforceソフトウェアエンジニアの役割

Salesforce開発会社とは？
[Salesforce開発会社](https://newwave-solutions.co.jp/salesforce-development-company/)は、企業がSalesforceを最大限に活用できるよう支援する専門企業です。主な業務には、Salesforceの導入サポート、カスタマイズ、他システムとの統合、継続的な保守とサポートが含まれます。これにより、企業は効果的な顧客関係管理（CRM）を実現できます。
Salesforceソフトウェアエンジニアの役割
[Salesforceソフトウェアエンジニア](https://newwave-solutions.co.jp/salesforce-software-engineer/)は、Salesforce開発会社で重要な役割を果たします。彼らの主な仕事は、Salesforceプラットフォームのカスタマイズと開発です。
主な業務内容
カスタムアプリケーションの開発: ApexやLightningを使用して、企業のニーズに応じたカスタムアプリケーションを開発します。
データベース管理: Salesforceのデータベース構造を設計し、効率的なデータ管理を行います。
インテグレーション: APIやミドルウェアを活用して、Salesforceを他のシステムと統合します。
ユーザーサポート: ユーザートレーニングやトラブルシューティングを提供します。
必要なスキル
プログラミングスキル: Apex、Visualforce、JavaScriptなどの知識。
データベース知識: Salesforceのデータベース設計やSQLの知識。
インテグレーション技術: API、SOAP、RESTに関する知識。
問題解決能力: 複雑な問題を解決する能力。
キャリアパス
Salesforceソフトウェアエンジニアは、技術力を磨くことで多くのキャリアチャンスを得ることができます。シニアソフトウェアエンジニア、アーキテクト、プロジェクトマネージャー、コンサルタントなどの道があります。
まとめ
Salesforce開発会社でのキャリアは成長の機会に満ちています。特にSalesforceソフトウェアエンジニアは企業の成長に貢献する重要な役割を担い、今後も高い需要が見込まれます。この分野でのキャリアは非常に魅力的で、多くの可能性が広がっています。
Azureのリソースを一覧で取得し、CSVファイルに出力する

# Azureのリソースを一覧で取得する
## 前提
- 最新のAzureCLIがインストールされていること

## 方法
以下のスクリプトファイルを保存し、PowerShellから実行する（.\GetResourcesList.ps1）

```PowerShell:GetResourcesList.ps1
<#
    .SYNOPSIS
        リソースを一覧で取得する

    .PARAMETER OutputFolderPath
        結果を出力するフォルダーの完全パス
        デフォルトは"CurrentDirectory\Outputs"

    .OUTPUTS
        ResourcesList_yyyyMMddhhmmss.csv

    .EXAMPLE
        PS> .\GetResourcesList.ps1
#>

Param(
    [Parameter(HelpMessage = '出力するフォルダのパス')]
    [String]$OutputFolderPath = (Get-Item $PSScriptRoot).FullName + '\Outputs'
)

$ErrorActionPreference = 'Stop'

# ログイン
az login

# 現在時刻
$CurrentTime = Get-Date -Format 'yyyyMMddHHmmss'

# フォルダチェック(フォルダが存在しない場合は新規作成する)
if (!(Test-Path -Path $OutputFolderPath -PathType Container)) {
    New-Item $OutputFolderPath -ItemType Directory
}

# 出力先のファイルパスを設定
$OutputFilePath = Join-Path `
    -Path $OutputFolderPath `
    -ChildPath ('ResourcesList_' + $CurrentTime + '.csv')

# 仮想マシンの一覧を取得する
$Resources = az resource list `
    --output json | ConvertFrom-Json

# CSVへ出力するためのオブジェクトを生成
$ResourcesList = New-Object System.Collections.ArrayList
$ResourceProperty = New-Object -TypeName PSObject

# CSVへ出力する情報をオブジェクトへ設定する
foreach ($resource in $Resources) {
    $ResourceProperty = @{
        'ResourceID'    = $resource.id
        'ResourceName'  = $resource.name
        'ResourceGroup' = $resource.resourceGroup
        'ResourceType'  = $resource.type
        'Location'      = $resource.location
        'Plan'          = $resource.plan
        'SKU'           = $resource.sku.name
        'ChangedTime'   = $resource.changedTime
        'CreatedTime'   = $resource.createdTime
    }
    $ResourcesList += New-Object PSObject `
        -Property $ResourceProperty
}

# CSVへ出力する
$ResourcesList `
| Select-Object `
    -Property 'ResourceID', `
    'ResourceName', `
    'ResourceGroup', `
    'ResourceType', `
    'Location', `
    'Plan', `
    'SKU', `
    'ChangedTime', `
    'CreatedTime' `
| Sort-Object `
    -Property ResourceGroup, `
    ResourceName, `
    CreatedTime `
| Export-Csv `
    -Path $OutputFilePath `
    -Encoding Default `
    -NoTypeInformation `
    -Force
```

## 概要
このコマンドで以下の情報を取得できる
- リソースID
- リソース名
- リソースグループ
- リソース種別
- リージョン
- プラン
- SKU
- 更新日時
- 作成日
新人エンジニアが会議であたふたしないための専門・ビジネス用語

## はじめに

20卒エンジニアとして入社して4年になります。
今では大抵の専門・ビジネス用語や略語は頭に入っていますが、入社したばかりの頃は会議中に慣れない言葉が飛び交い、その意味を調べている間に会話から置いていかれるというシチュエーションが何度かありました。

今回は、個人的に頻出度が高く、「あらかじめ知っておけばよかった！」と思った専門・ビジネス用語をピックアップしてご紹介します。

## カタカナ語系

|用語|意味|
|---|---|
|オンスケ<br>(on schedule)|予定通り|
|リスケ<br>(reschedule)|アポイントメントや会議などの日程変更、調整、納期の延長|
|バッファ<br>(buffer)|余裕、緩衝|
|アジェンダ<br>(agenda)|予定表、会議の議題として予定している内容をまとめたもの|
|レジュメ<br>(resume)|会議の内容などをまとめたもの|
|サマリー<br>(summary)|会議の内容などをまとめたもの|
|アサイン<br>(assign)|任命する、割り当てる|
|フィックス<br>(fix)|確定する、決定する|
|シームレス<br>(seamless)|縫い目のない、垣根のない|
|インシデント<br>(incident)|出来事・事件|
|ローンチ<br>(launch)|発売する、公開する、開始する|
|エビデンス<br>(evidence)|根拠、証拠|
|コミット<br>(commit)|責任を持って取り組む、約束する|
|クリティカル<br>(critical)|重大な、致命的な|
|リソース<br>(resource)|資源、時間、情報、人材|
|ブラッシュアップ<br>(brush up)|磨き上げる、完成度を高める|
|シナジー<br>(synergy)|相乗効果|
|ステークホルダー<br>(stake holder)|利害関係者|

### コラム:アジェンダ・レジュメ・サマリーの違い

|用語|作成・配布タイミング|目的|
|---|---|---|
|アジェンダ<br>(agenda)|会議前|時間配分の把握、会議そのものの進行の円滑化|
|レジュメ<br>(resume)|会議前|議題の把握、会議中のやり取りの円滑化|
|サマリー<br>(summary)|会議後|会議内容の把握、短時間での共有|

## 頭字語系

|用語|意味|
|---|---|
|ASAP<br>(as soon as possible)|できるだけ早く|
|MTG<br>(meeting)|ミーティング、会議|
|OJT<br>(on the job training)|職業訓練|
|FAQ<br>(frequently asked questions)|よくある質問|
|B2B<br>(business to business)|企業間の取引|
|B2C<br>(business to customer)|企業と一般消費者(顧客)の取引|
|C2C<br>(consumer to consumer)|一般消費者間の取引|
|SES<br>(system engineering service)|システム開発や保守・運用などの業務に対してエンジニアを提供するサービス、客先常駐|
|SIer<br>(system integrator)|システム開発や保守・運用などの業務を請け負う企業|

## ほかにも

|用語|意味|
|---|---|
|決め打ち|結論や展開、予定を事前に決めておき、それに基づいて実行すること|
|空中戦|互いの意見を文字に起こすことなく、口頭のみで議論すること|
|座組み|プロジェクトや組織に関わる人など、ビジネス構造全般を表す|
|ペライチ|1ページのみのWebページや資料のこと|
|銀の弾丸|問題を一撃で解決できる万能な解決方法|
|交通整理|煩雑になった業務内容などの情報を整理すること|
|カニバる|「共食い」を意味する「カニバリゼーション(cannibalization)」を由来とするビジネススラング。自社競合を起こす|

## さいごに

個人的に頻出度が高いと思う専門・ビジネス用語をピックアップしましたが、会社それぞれの慣習・文化によって頻出度は大きく変わり、さらには社内でしか聞かないような用語を使用するパターンも多くあります。
そういった用語をキャッチアップすることで、より早く会議での円滑なコミュニケーションが取れるようになると思います！
「答えを見る」という正義

# はじめに
こんにちは！文系で未経験にもかかわらずエンジニアとして働くことになったitaaaaです。

エンジニアとして研修を受けている現在、当然のように毎日コードについて知識を入れたり書いてみたり…と勉強の毎日を送っています。

今回はその中で見つけた（というよりも**有用さを再認識した**）コードについての勉強法についてお話ししようと思います。

自分と同じ様にゼロから何かを学んでいる人にはもちろん、改めて勉強している人にも読んでもらえると嬉しいです。

# 「答えを見る」ことのすゝめ
さて突然ですが、「答えを見る」と聞いたときに、皆さんどのような感情を抱きますか？

「褒められることではない」と感じる方もいるでしょう。
あるいは、「課題提出を間に合わせるために、答えを見ながらうまいこと○を付けるところと×を付けるところを組み合わせて～」なんてことをした人もいるかもしれません。

一般的に、「答えを見る」という行為は「後ろめたいもの」だと捉えられている、と私は思います。

ですが、こと「0から学ぶ」という点において、**答えを見ることは効率よく学ぶための武器**となるのです。

# コードの”型”
話は少し変わりますが、私は「**コードには”型”が存在する**」と思っています。

ここで私が「型」というのは、このような出力を求められたら、このようなコードを書く、といったものです。
より具体的には「Hello, world!」と出力しろ、と言われたらSystem.out.println()を使う、といったものです。

つまり、「この処理にはこのコードを書く」といった**考え方のひな型**のようなものがコードには存在します。
このことを「コードの型」と表現しているのです。

そして、この型を知るにあたって、**「答えを見る」ことは大きな効力**を持っています。

# コードの型を知るための「答え」
ここで少し想像してみてください。

ここに、コードについて全く知識を持たない新米未経験エンジニアのitaaaaがいます。
当然、この人はコードの型など知るはずもありません。

研修において「Hello, world!」と出力しろ、と課題が出たので、itaaaaは長時間かけて自力でメソッドなどを調べ、この課題をクリアしました。
<br>
さて、皆さんどう感じましたか？未経験エンジニアが頑張って自力で課題をクリアした、という点では微笑ましいですが**あまりに非効率**でもあります。

あるいは、「println()くらい調べればすぐわかるでしょ」と感じた方もいらっしゃると思います。

では、この課題内容が下記サイトの問題(paizaのC問題)くらいの難易度だったらどうですか？

https://paiza.jp/works/mondai/data_structure/data_structure__dict_boss/edit?language_uid=java

これを自力で調べ上げたとしたらどれだけ時間がかかるのでしょうか？考えたくもないですね。
<br>
先ほど述べた通り、コードには型があります。
つまり、先ほどitaaaaが頭を悩ませて導いた回答は**自明のもの**であり、そこに**大きな生産性はありません。**

もちろん、自力で調べ上げたその時間に価値がないわけではないですが、効率的であるとは言えません。

自明の解き方が存在するのであれば、つまりはコードの型が存在するのであれば、**それを知ること**が肝要であり、それこそが**コードの勉強**であると私は考えます。

そして、コードの型を知るための最も効率的な手段が**答えを見る**ことだと考えるのです。

# 「答えを見る」勉強法
ここまで、コードの勉強とは「コードの型を知ること」であり、コードの型を知るためには「答えを見る」のが一番だと話してきました。

では一体どのようにして、答えを見ることを学習の中に組み込めばよいのでしょうか？

学習の中に「答えを見る」ことを組み込むには**答えをうまく使う**必要があります。
具体的には次のような流れの学習方法です。
<br>
1. 時間を決めて（長くても10~20分程度）問題の解き方の方針を決める。時間を超えたら3.へ進む
2. 時間を決めて（長くても10~20分程度）問題を解く。時間を超えたら3.へ進む
3. 答えを見て、**知らなかった考え方やメソッドを1つずつまとめる**
4. まとめたものについて調べ、**自分なりの理解をまとめる**
<br>
当然ですが、ただ答えを見るだけでは知識の定着にはなりません。<br>
「答えを見て終わり」にさせないために、「何がわからなかったか」「何をあたらしく学んだのか」をリストアップし、それぞれに対して自分で調べることで、知識を定着させることができ、将来「これが使えそう！」と考えるトリガーになるのです。<br>
これこそが、コードの型を覚え次に活かす「答えの上手な使い方」なのです。

# さいごに
長々とご精読いただきましてありがとうございました。

「答えを見て勉強する」という字面は少し驚くようなものかもしれませんが、実際は効率をぐんと上げられるものだと思っています。
大仰に言っていますが、「答えを見るなんて、もうやってるよ」という人のほうが多いかもしれませんね。

少し話はそれますが、コードの勉強は数学の勉強に似ていると私は確信しています。
どちらも、明確な回答方法があり（つまり回答法のひな型があり）、いろいろな要素を組み合わせて回答にたどり着く、という特徴を持っています。

この勉強法は、文系だけど数学も受験で使っていた私が大学受験期に濫用した手法です。1Aも2Bも、青チャートが嫌いになるほど、何週もこの手法を用いて勉強してきました。

その方法で大学に受かった自分としては、この勉強法は**確かに効果がある**ものであり、有効であると太鼓判を押したいと思い、今回筆を執りました。

この記事が誰かの役に立つことを願いつつ、この記事を締めさせていただきます。
改めまして、ご精読いただきありがとうございました。

それでは！
ファイルパス・作業ディレクトリのコピペ問題

# ■はじめに

永遠のプログラミング初心者なので、何年もファイルパスの指定でアホの処理の仕方をしている。

## まずPythonでは？

普通にファイルパスをコピペしてくるとこうなる。これで普通に動いてほしい。
```python
"C:\Users\XXXXX\Desktop\XXXXX\XXXXX.pdf"
```

しかしpythonはこれでは動いてくれないので、ずっと毎回手動で`\`を`/`に直してきた。
「理由は知らんが、`\`を`/`に直せば動く」という事実だけは経験から学習しているので、毎回手動の力業でどうにかしてきたが、さすがにアホすぎる。

```python
pdf_document = 'C:/Users/XXXXXXX/Desktop/xxxx.pdf'
``` 

## Rでは？

```R
setwd("C:\Users\XXXXX\Desktop\working directory\20220407_作業用")
getwd()
```
Rでも`\`では動いてくれない。

```R
setwd("C:/Users/XXXXXX/Desktop/working directory")
getwd()
```
Rでも`/`なら動いてくれる。

# ■やること
プログラミングにおいて私が「めんどくさ～～～」と思うことは100%誰かが解決してくれている。ということで、下記の内容を行う：

・`\`ではダメな理由を理解する
・`\`を`/`に直せば動く理由を理解する
・「毎回手動で直す」以外の対処方法を確認する

# ■`\`ではダメな理由、`\`を`/`に直せば動く理由
Pythonでは、バックスラッシュ（`\`）はエスケープ文字として機能する。
これは、特定の文字列を特別な文字（例えば、改行を表す`\n`やタブを表す`\t`など）として解釈するために使用される。
そのため、ファイルパスにバックスラッシュが含まれていると、Pythonはそれをエスケープシーケンスとして解釈しようとしてくれる。




# ■「毎回手動で直す」以外の対処方法

## Pythonの場合：頭文字「r」を付ける
文字列の最初に「そのまま」という意味の「raw」の頭文字「r」をつける。
これにより、エスケープシーケンスが行われず、そのままの文字列として扱われるようになる。

```python
r'C:\Users\XXXXXX\Desktop\XXXXX\XXXXX.pdf'
```

この方法を使えば、手動でパスを修正する必要はなくなる。簡単～～:relaxed:便利～～:relaxed:

## Rの場合：手動しかない
Rのsetwd関数を使用する際に、Windowsのファイルパスにはバックスラッシュ（\）が含まれているが、これはRのエスケープ文字として解釈されるため、正しくパスを認識させるためには各バックスラッシュをダブルバックスラッシュ（\\）にするか、またはフォワードスラッシュ（/）を使用する必要がある。
さらに、文字列リテラルとしてパスを指定する際には、ダブルクォーテーション（"）を使用する。

頭文字「r」をつける方法とは、リテラル文字列の前に小文字の「r」を付けて、その文字列内のエスケープシーケンスを無効にする方法だが、これはPythonの文字列リテラルにおけるraw文字列の記法であり、R言語には適用されない。

したがって、Rで正しいファイルパスを指定するには以下のように書き換える：

```R
setwd("C:\\Users\\u1115885\\Desktop\\working directory\\20220407_作業用")

# または

setwd("C:/Users/u1115885/Desktop/working directory/20220407_作業用")
```
どちらの方法もRでファイルパスを正しく認識させられるが、手動対応でやるしかない。
この処理を一発でできるコマンドもないようである。

# ■感想

筆者が初めて触ったプログラミング言語がRだったため、ファイルパスは手動で直すのが普通だと思っていたが、Pythonではそうではないということが分かった。RとPythonの違いを発見することができてうれしい。

ぶっちゃけ動けばなんでもいいんだけど、ずっと「めんどくさ～～～」と思っていたことの理由と対処方法が分かると気持ち良い。



# ■参考

https://qiita.com/hajimejimejime/items/93a9c4bb3bf009e89924

# ■追記

最近追加された機能で、Rにもraw文字列があるので手動じゃなくてもできるかもと教えてもらいました。

https://r4ds.hadley.nz/strings#sec-raw-strings
windowsのターミナルでリダイレクト処理をするとカンマがおかしくなる

# デフォルトでカンマ区切りにならない
数値を出力する記述をしたCファイルをコンパイルしたexeファイルをwindows11からデフォルトとなったターミナル(PowerShell)で実行し，手頃なCSVファイルにリダイレクトし，このCSVファイルをexcelで開くと次のような形式で出てくる．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3125214/86ebd360-cae0-5d46-b876-544f32be0eef.png)

少しでもエンジニアに足を突っ込んでいる人ならカンマ区切りにすればいいんじゃないの？と言うと思うが，コマンドプロンプト(ターミナルでない)で同じ処理をすると次のようになる．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3125214/3b46bfb3-8139-90de-08cf-66edbe9bcf63.png)

そう，デフォルト区切り文字にカンマが指定された状態で出てくるのである．

つまりファイルの状態ではこのカンマ少しおかしいのである．
他にもC言語のstrtok関数においてカンマを区切り文字として指定した場合にもカンマとして見てくれないのである．

# 原因
こうなる原因はおそらく出力先のフォント形式によるものだと思われる．

|CUI|フォント形式|カンマ|
|:--|:--|:--|
|コマンドプロンプト|等幅フォント|無事|
|ターミナル(win11)|プロポーショナルフォント|だめ|
|ターミナル(VScode)|プロポーショナルフォント|だめ|

このようにフォント形式とカンマの状態が連動している．そもそもターミナルがだめなのかもしれないけどね．

# 解決策
フォント等の変更を試みたりもしてみたが，コマンドプロンプトを使う他ない．終わりです．

技術力が上がって根本的な解決ができるようになったら解決します．
Amazon  Athenaで日付でパーティション射影をする

webエンジニアの風速です。
今回はAmazon Athenaを業務内で使用して日付でパーティションの射影をするのに苦労したので、そちらをまとめられたらと思います。

# Amazon Athenaとは
Amazon Athenaは、SQLを使用してS3内のデータを直接分析に利用できたりするクエリサービスです。サーバーレスで、読み込んだ容量に応じて課金されるシステムになっています。データ1TBあたり5.00USDらしい（ap-northeast-1）
S3内のcsvなどのデータを読み込んで実際のrdbのテーブルのように操作可能です。

# パーティションとは
パーティションという機能はAthena以外にもrdbの機能にあるもので（調べて初めて知った）、テーブル内のデータを格納する場所を分けられる機能です。
Athenaでは読み込むデータによって課金されるため、デイリーとかで動かす場合はかなり重要で、公式も料金かなり削減できると言ってます。

# パーティション射影とは
S3のディレクトリを自動的にパーティション分けしてくれる機能です。テーブル定義のときに設定を書くと、その形式でパーティションを追加してくれます。実際にはテーブルのカラムに追加されるようなイメージ。

# テーブル定義
```
CREATE EXTERNAL TABLE IF NOT EXISTS `test_db`.`test_table` (
  `test_column1` string,
  `test_column2` string,
  `test_column3` string,
)
PARTITIONED BY ( 
  `partition_date` string, 
)
ROW FORMAT SERDE 'org.apache.hadoop.hive.serde2.OpenCSVSerde'
WITH SERDEPROPERTIES (
  'separatorChar' = ',',
  'quoteChar' = '\"',
  'escapeChar' = '\\'
)
LOCATION 's3://test-stor/'
TBLPROPERTIES (
  'projection.enabled'='true', 
  'projection.partition_date.type'='date', 
  'projection.partition_date.format'='yyyy/MM/dd/HH', 
  'projection.partition_date.interval'='1', 
  'projection.partition_date.interval.unit'='HOURS', 
  'projection.partition_date.range'='2024/06/18/00/,NOW', 
  'storage.location.template'='s3://test-stor/${partition_date}/', 
  'write.compression'='GZIP'
);
```

今回は非Hive形式で格納されているcsvファイルを解析するテーブルを使用します。
s3上の`test-stor`バケットに以下のようにディレクトリ分けされているのを想定しています。
```
s3://test-stor/yyyy/MM/dd/HH/test.csv
```

`PARTITIONED BY`句のところにパーティション射影したい名前を定義します。

`'projection.enabled'`はパーティション射影をするかの設定です。

`projection.partition_date.type`はパーティションする型で今回は日付でパーティションしたいので`'date'`としています。ほかにも型はありますが今回は紹介しません。

`'projection.partition_date.format'`はパーティションするディレクトリの日付の形式を指定します。

`'projection.partition_date.interval'`はパーティションする間隔を設定できます。今回は1としているので、`'projection.partition_date.interval.unit'`がHOURSなので1時間ごとにパーティションを作成するという設定になっています。

`'projection.partition_date.range'`は`'from,to'`のイメージで、to側にNOWとすると、現在の時刻をfromとしてくれます。ただUTCなので取得する際は時差に注意が必要です。

`'storage.location.template'`はパーティションしたいディレクトリを指定します。
ディレクトリの直下すべてが対象となるので、パーティションしたディレクトリ以下の構成はいろいろ分けても大丈夫だと思いますが、除外設定等できないと思うので、違ったファイル形式のものを置くのは避けた方が良いと思います。

# SELECTの例
以下のようにpartition_dateをWHEREの条件に指定でき、対象のディレクトリにあるファイルを読み込んでくれます。
```
SELECT
    test_column1,
    test_column2,
    test_column3
FROM
    test_table
WHERE
    test_table.partition_date = '2024/06/18/01'
```

# まとめ
パーティション射影はかなり楽にパーティションを作成でき、読み込むファイルも節約できるのですが、設定のドキュメントが個人的に分かりにくかったので、今回の記事を作成しました。すこしでも参考になれば幸いです。

# 参考
https://docs.aws.amazon.com/ja_jp/athena/latest/ug/partition-projection-supported-types.html

https://dev.classmethod.jp/articles/when-does-athena-partition-projection-work/
neoAIの最新モデルをollamaで動かしてみたよ (Llama-3-neoAI-8b-chat-v0.1)

# 概要
[株式会社neoAI様](https://neoai.jp)より新しいLLMが発表されたので、ollamaで試してみました。

# 関連情報

 - X(旧Twitter)にて、うたたね|[neoAI Inc.](https://neoai.jp/)様のツイート

https://x.com/dream_utatane/status/1805820901885460729

 - HuggingFace

https://huggingface.co/neoai-inc/Llama-3-neoAI-8B-Chat-v0.1

 - 早くもggufが早速公開されている

https://huggingface.co/NikolayKozloff

https://huggingface.co/mradermacher/Llama-3-neoAI-8B-Chat-v0.1-GGUF

# やったこと(手順)

### ggufファイルをダウンロード
  ブラウザでggufファイルをダウンロードする

### ディレクトリを作って移動
```bash
$ mkdir foo/neoai-8b-chat
$ mv ~/Download/llama-3-neoai-8b-chat-v0.1-q4_0.gguf ./
```

### Modelfileを作る
ollamaにインポートするためにMakefileが必要らしい。よくわからないけど、FROMだけあればとりあえず動くらしいぞ。(最後に参考資料)
```text:Modelfile
FROM ./llama-3-neoai-8b-chat-v0.1-q4_0.gguf
```
いずれ誰かがollamaのリポジトリに登録してくれるでしょうから、それまではこれで。

### ollamaにモデルを登録する
```bash
$ ollama create neoai-8b-chat -f Modelfile
transferring model data 
using autodetected template llama3-instruct 
using existing layer sha256:3796d053c5663043b83841b5b4340aa6991b3433f981e9f564d7bed68a73aaa9 
creating new layer sha256:23559df12bfb1da7e6a0a3d2725f0f3ed51590d856ff3bc67a0a4a7fb080d648 
writing manifest 
success
```

### 出来たっぽい？
```bash
$ ollama ls
NAME                                         	ID          	SIZE  	MODIFIED       
neoai-8b-chat:latest                         	6096cf33fd74	4.7 GB	41 minutes ago	
hawkclaws/datapilot-arrowpro-7b-kujira:latest	873301a15d62	7.7 GB	2 weeks ago   	
phi3:latest                                  	64c1188f2485	2.4 GB	2 weeks ago   
```

### 実行してお話してみる
```bash
    $ ollama run neoai-8b-chat
    >>> やっほお
    こんにちは！何をおそがえになったのか？

    >>> うんちしたい
    トイレに行くか？

    >>> トイレ使用中。こまったこまった
    おそらく、トイレでこまるのは不快だと思う。早く戻れるといいね！

    >>> かに食べ放題についてどう思う？
    私は言語モデルであり、人間ではないので、食べ物についての個的な
    意見はありません。また、私は感情やバイアスを持っていません。私
    ができるのは、あなたが考えることがあることについて知識を提供す
    ることです。したがって、「カニを無制限に食べることはできますか
    ？」、「カニを食べることは快楽であるかもしれませんか？」、「カ
    ニは健康に良いですか？」などの質問の回答を提供できます。

    >>> カニを無制限に食べることはできますか？
    それは、人それぞれであり、身体的、精神的健康に影響を与える可能
    性があります。また、カニは一般的に高脂肪と高タンパク質であるた
    め、食物アレルギーや消化不協lianceを持っている人は、それらが
    彼らの健康にとって良いことか悪いことかについて疑問を持つかもし
    れません。

    >>> Send a message (/? for help)

```

### 終わったから消しちゃう
```bash
    $ ollama rm neoai-8b-chat
```

### ちなみに
ollamaのリポジトリからダウンロードしたモデルは、/usr/share/ollama/.ollamaに格納されるようだぞ。
```bash
# cd /usr/share/ollama
# find . -type d
.
./.mozilla
./.mozilla/extensions
./.mozilla/plugins
./lib
./lib/rocm
./lib/rocm/rocblas
./lib/rocm/rocblas/library
./.ollama
./.ollama/models
./.ollama/models/blobs
./.ollama/models/manifests
./.ollama/models/manifests/registry.ollama.ai
./.ollama/models/manifests/registry.ollama.ai/library
./.ollama/models/manifests/registry.ollama.ai/library/phi3
./.ollama/models/manifests/registry.ollama.ai/hawkclaws
./.ollama/models/manifests/registry.ollama.ai/hawkclaws/datapilot-arrowpro-7b-kujira
```

# 参考資料

https://github.com/ollama/ollama/blob/main/docs/modelfile.md

https://qiita.com/kiyotaman/items/2effed548e7be32da546

https://zenn.dev/hellorusk/articles/94bf32ea09ba26
意外と簡単なVSCode拡張機能の作り方

こんにちは、WEBエンジニアの堀井です。

私が仕事で普段から愛用しているエディターVisual Studio Code（通称VSCode）。
このエディターを使っている理由の一つに拡張機能があります。
拡張機能を使うことで開発がとてもやりやすくなるのです。

そんな拡張機能、既に様々なものが公開されていますが、痒いところに手が届かないなんてこともあるかもしれません。

そんな時は自作してしまいましょう。

今回はその第一歩としてHelloWorldを実行するところまでやってみます。

## 準備

拡張機能の開発の前に以下を準備しておきましょう。
* VSCode
* Node.js と git のインストール

## プロジェクトの作成

まずは Yeoman というスキャフォールディングツールを利用して雛形を作成するため、以下コマンドを実行します。

```
npx --package yo --package generator-code -- yo code
```

おじさんが出てきて色々聞かれるので、今回は画像のようにしました。

![vscodeext.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3780649/596d4d34-e54d-136c-2a6f-60dde899e018.png)

するとhelloworldプロジェクトが作成されます。

## 実行

先ほど作成したhellowprldプロジェクトをVSCodeで開き、左の「実行とデバッグ」タブの「実行とデバッグ」を押すと新たにVSCodeが起動します。

そこで「command + shift + P」でコマンドパレットを表示し、「HelloWorld」を選択すると右下に通知が表示されます。

![スクリーンショット 2024-06-27 0.44.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3780649/7b9fc5a8-f4da-57af-d50d-e442a0fa22c8.png)

これで拡張機能が動くことが確認できました。

## まとめ

今回はVSCodeの拡張機能を作成してHelloWorldを表示してみました。

といってもスキャフォールディングツールを利用しただけなのでほぼ何もしてませんが、それでもVSCodeの拡張機能ができたことには変わりありません。

これで基本的なVSCode拡張機能の作り方がわかったと思いますので、これを応用して自身の作りたい拡張機能を作成してみてはいかがでしょうか？

最後に、本格的に拡張機能を作成したい方は[こちら](https://github.com/microsoft/vscode-extension-samples)にサンプルがたくさんありますので、そちらを参考にしてみてください。

以上、堀井でした。

## 参考

* https://code.visualstudio.com/api/get-started/your-first-extension
【ChatGPT＋DALL-E3】で複数画像から動画を作成します。


　どうも、カーブミラーです。

　今回は、複数の画像から動画を作成します。スライドショーみたいな感じでしょうか。

:::note info
本記事は、ChatGPT（有料版）
＋DALL-E3で行なっております。
画像はありません。あしからず。
:::

　まずは、ニュース。

　FigmaにAI機能が付きました。
　　[dyson / designerさんポスト](https://x.com/web_tsutsui/status/1806116811169239177?t=tQE-PbxdlITLD0urlwv4OA&s=03)

　Figmaとは、
　　ブラウザ上で
　　　簡単にデザインができるツール
　　　　だそうです。

　一時期、X-Twitter上で
　　話題になっていましたが、
　　　ここのところ、
　　　　静かでした。

　そこに
　　新機能とともに
　　　AI機能が加わるそうです。
***
　さて、
　　本題です。

　複数の画像をつなげて、
　　映像にしたいことがあります。

　通常、ほかのツールで
　　行ないますが、
　　　ChatGPTでも
　　　　行なえます。

　手順は
　❶複数の画像をアップロード
　❷Prompt入力
```Text:複数画像→動画Prompt
MoviePyを使って、これらの画像を動画にしてください。
```
　❸送信
　❹ダウンロード

　これだと、
　　ひとつの画像を二秒、
　　　それからパッと切り替わります。

　切り替えの仕方には
　　トランジションエフェクトが
　　　使えます。

　いくつかありますが
　　試した感じ、以下のふたつだけが
　　　処理に成功しました。

　・フェードイン・フェードアウト
　・ズーム

　こちらのPromptの
　　✘✘✘部分をどちらかに
　　　書き換えてください。
```Text:複数画像→動画・改Prompt
MoviePyを使って、これらの画像を動画にしてください。
なお、切り替え時にトランジションエフェクト（✘✘✘）を使ってください。
```

　みなさんの
　　作品制作の糧に
　　　なれば、幸いです。

　今回は、ここまで。
【Python】俺「loggingのloggerモジュールってどこでインスタンス化すればいいんですか？logger_util.pyとかですか？」

俺「loggingのloggerモジュールってどこでインスタンス化すればいいんですか？logger_util.pyとかですか？」

答え：Loggerオブジェクトは、**もうある。**
logging.getLogger()を使ってLoggerオブジェクトを取得する。これにより、新しいLoggerを作成するのではなく、既存のLoggerを取得するか、必要に応じて新しいLoggerを生成する。

>loggingは1つのpython.exeに対して1人のみ存在する

https://zenn.dev/dencyu/articles/2b58f669bcd473

自分のPythonのloggingの認識や使い方が誤っていたので、メモ。

### 正解例

- 宣言の一例（basicConfigを指定して、簡単なフォーマットだけしたい）

```python
import logging

# Loggingの初期化
logging.basicConfig(
        level=logging.INFO,
        format="%(asctime)s - %(levelname)s - %(message)s",
        handlers=[
            logging.StreamHandler()
        ]        
)

logger = logging.getLogger(__name__)
```

もっと詳しい制御をやりたいときはyamlファイルで指定することになる。
フォーマットのみしたい、とか、そういう話ならこれでよさそう。

### 使用例

```python
from logging import getLogger
logger = getLogger(__name__)
logger.info("ここにLog")
```
`logging.info`とやるとルートLoggerさんが呼び出されてしまう。しかしloggingを単にインポートするだけだとやらかしがちなのであえてgetLoggerだけ使えるようにしておく。

https://qiita.com/amedama/items/b856b2f30c2f38665701

# ミスの原因
- よくわからないままloggingを便利モジュールとして使っていた(調べてみると、結構奥が深い話だった。)
- C#のいつもの慣習
普段、C#での開発ではログの出力用のクラスを、program.csあたりでインスタンス化し、使用していた。この感覚でPythonのロギングをしようとしていたので、失敗した。
- ChatGPTがこのトピックについてさほど詳しくない
Pythonのロギングは出るようにするだけなら割と正しくなくても動くため、あたかも実装できたかのように見えてしまう。こっちがミスったまま出力をお願いしてるとヘンな出し方をする。

# 参考
[Logging HOWTO](https://docs.python.org/ja/3/howto/logging.html)
公式のチュートリアルだがやや難しい。

[ログ出力のための print と import logging はやめてほしい](https://qiita.com/amedama/items/b856b2f30c2f38665701)
とても詳しい。

[Pythonのloggingをイメージで理解する【Python Logging徹底解説】](https://zenn.dev/dencyu/articles/2b58f669bcd473)
Loggingがこのプロジェクトだけではなく全体で動いていることがとても分かりやすい。

[Pythonでprintを卒業してログ出力をいい感じにする](https://qiita.com/FukuharaYohei/items/92795107032c8c0bfd19)
端的でわかりやすい。

※本記事はQmonus Value Streamの投稿キャンペーン記事です。

https://qiita.com/official-events/3648bc4e6cedb674491c
【VSCode ショートカットキー】初心者がまず絶対に押さえておきたい生産性爆上げショートカットキー10選

## 主な想定読者
最近VSCodeを使い始めたプログラミング初心者

## 概要
筆者が普段から頻繁に使用しており、便利で重宝しているショートカットキーを、完全な独断と偏見で10個厳選しました！
※Ctrl+C, Ctrl+V（コピー, ペースト）など、あまりにも有名で、すでに多くの方がご存知であろうショートカットキーは除いております。

## ショートカットキー10選（一覧）
| ショートカットキー | 動作 |
|:-----------|------------:|
| Alt + ↑↓     | 行の移動      |
| Shift + Alt + ↑↓       | 行のコピー        |
| Ctrl + Shift + K         | 行の削除          |
| Ctrl + [ / ]       | インデントの追加/削除        |
| Ctrl + /       | コメントアウト/解除       |
| Ctrl + D    | 単語選択     |
| Ctrl + Shift + L    | 同じ単語を全て選択     |
| Ctrl + PgUp/PgDn    | タブの切り替え     |
| F12（またはCtrl + クリック）    | 定義へ移動     |
| Ctrl + P    | ファイルのクイックオープン     |

## ショートカットキー10選（詳細）
### 1. `Alt + ↑↓` - 行の移動
行全体を上下に移動することができるショートカットキーです。素早く行全体を移動可能。行ごと移動させたい時に、行を切り取って挿入したい箇所に貼り付ける、といった操作が不要となります。
### 2. `Shift + Alt + ↑↓` - 行のコピー
カーソルが置かれた行をコピーし、そのまま上下の行に挿入できます。同じようなコードを複数箇所で書きたい時などに、役立ちます。
### 3. `Ctrl + Shift + K` - 行の削除
カーソルが置かれている行を一瞬で削除してくれます。複数行を選択すれば、複数行削除も可能。
### 4. `Ctrl + [ / ]` - インデントの追加/削除
手動でインデントを揃える手間が省けて、コードが整理整頓された状態を保ちやすくなります。
### 5. `Ctrl + /` - コメントアウト/解除
コメントアウト、既存コメントの解除が簡単に行えます。特定のコードを一時的に無効化したい時などにとても便利です。
### 6. `Ctrl + D` - 単語選択
現在カーソルが置かれている単語を選択します。`Ctrl + D`を複数回叩くことで同じ単語が複数選択されるので、複数個所に散らばっている同じ単語を、1度にまとめて編集したい時に役立ちます。
### 7. `Ctrl + Shift + L` - 同じ単語を全て選択
`Ctrl+D`の一括版。カーソルが置かれている単語と同じ単語を全て選択します。変数名を一括で変更する時などに大活躍します。
### 8. `Ctrl + PgUp/PgDn` - タブの切り替え
複数のタブを開いている時に、タブを素早く切り替えられます。
### 9. `F12`（または`Ctrl + クリック`） - 定義へ移動
メソッドや変数にカーソルを置いた状態で`F12`を押すと、そのメソッドや変数が宣言されている定義場所へジャンプしてくれます。わざわざファイルを開いて探したりせずとも、メソッドや変数の定義を参照できます。
### 10. `Ctrl + P` - ファイルのクイックオープン
ファイル検索のショートカットキーです。ファイル名の一部を入力するだけで、素早くファイルを開くことができます。特に、扱うファイル数が多い時に便利です。

## おわりに
以上、VSCode初心者におすすめの、生産性爆上げショートカットキー10選でした。ショートカットキーを駆使して、生産性を爆上げしましょう！
最後までお読み頂き、ありがとうございました！