OmniAICreator/Qiita-1.07M huggingface dataset:
【React】「React children」を紐解く【children】

# はじめに

基本的な”props”や”コンポーネント”・”state”あたりは簡単に学習を済ませた私が、React.childrenで躓いたので使い方を確認しながら学ぶ記事です。

# TL;DR

props.children：子要素の出力が可能

React.children：`this.props.children` を扱うためのユーティリティ（便利なもの）を提供するAPI

# 躓いた箇所

```jsx
function FancyBorder(props) {
  return (
    <div className={'FancyBorder FancyBorder-' + props.color}>
      {props.children}
    </div>
  );
}

function WelcomeDialog() {
  return (
    <FancyBorder color="blue">
      <h1 className="Dialog-title">
        Welcome
      </h1>
      <p className="Dialog-message">
        Thank you for visiting our spacecraft!
      </p>
    </FancyBorder>
  );
}
```

上記のコードを見た時、
（（FancyBorderにpropsとして渡してるのってcolorだけなのに、なんかprops.childrenって書いてる・・・え、どこからchildren来たの・・・？））
このように戸惑ってしまいました。

FancyBorderのprops.childrenに表示されるものは、こちら。
ポイントは、**FancyBorderの子要素**だということ。
```jsx
<h1 className="Dialog-title">
　　Welcome
</h1>
<p className="Dialog-message">
　　Thank you for visiting our spacecraft!
</p>
```

# Reactのchildrenとは

子要素を出力することができるpropsのこと。
[https://ja.reactjs.org/docs/composition-vs-inheritance.html#containment](https://ja.reactjs.org/docs/composition-vs-inheritance.html#containment)（公式）
```jsx
// 明示的に値を渡す必要が無い
<FancyBorder color="blue">
```
上記のように**明示的にpropsへ値を渡さずとも**、Reactが勝手に読み取ってくれます。

# React.childrenって何？

childrenのことはよく理解できた！…と思いきや、調べていくと
props.childrenの他に**React.children**を発見しました。
React.childrenとは何なのか、またどのように使用するのか見ていきます。

## React.childrenとは

`this.props.children` を扱うためのユーティリティを提供するAPI
[https://ja.reactjs.org/docs/react-api.html#reactchildren](https://ja.reactjs.org/docs/react-api.html#reactchildren)（公式）

私はこの公式の説明だけでは理解が出来なかったので、もう少し公式を読み進めてみます。
すると下記のような説明がありました。

- **`React.Children.map`**
`this` を `thisArg` に設定して、`children` 内に含まれるすべての直下の子要素に対して関数を呼び出す。

```jsx
React.Children.map(children, function[(thisArg)])
```

- **`React.Children.forEach`**
`[React.Children.map()](https://ja.reactjs.org/docs/react-api.html#reactchildrenmap)` と似ているが、配列を返さない。

```jsx
React.Children.forEach(children, function[(thisArg)])
```

- **`React.Children.count`**
`children` に含まれるコンポーネントの総数を返す。これは `map` または `forEach` に渡したコールバックが呼ばれる回数と同じ。

```jsx
React.Children.count(children)
```

`React.children`は、取得した子要素をアレコレ操作することができる便利なAPIでした。

# さいごに
React childrenを知ってから、Reactのコードを少し読みやすくなりました。
他にもたくさん分からない事があるので、一つずつ理解して、理想的なUIを作成していきたいと思います！

# 🙏参考リンク

[https://ja.reactjs.org/docs/composition-vs-inheritance.html](https://ja.reactjs.org/docs/composition-vs-inheritance.html)
[https://ja.reactjs.org/docs/react-api.html#reactchildren](https://ja.reactjs.org/docs/react-api.html#reactchildren)
［統計検定準1級］ワークブック4章例題解説

# 問4.1
問題本文はワークブック参照

## 復習

問題を解く前に今回扱う範囲をおさらいします。
今回の問題は正規分布の性質について押さえておけば解けますが、問題全体が正規分布から対数正規分布のあれこれを導出する内容のため、対数正規分布の性質についても紹介します。

#### ■正規分布(normal distribution)
- **確率密度関数**：
$$
f(x)=\frac{1}{\sqrt{2\pi}\sigma}\exp\left(-\frac{(x-\mu)^2}{2\sigma^2}\right)
$$
- $X\sim{N}(\mu,\sigma^2)$ のとき
    - **平均**：$E[X]=\mu$
    - **分散**：$V[X]=\sigma^2$
    - **モーメント母関数**：
$$
M(t)=E[\exp(tX)]=\exp\left(\mu{t}+\frac{\sigma^2t^2}{2}\right),~-\infty<{t}<\infty
$$

#### ■対数正規分布(log-normal distribution)
- **確率密度関数**：
$$
f(x)=\frac{1}{\sqrt{2\pi}\sigma{x}}\exp\left(-\frac{(\log{x}-\mu)^2}{2\sigma^2}\right),~x>0
$$
- $X\sim{\varLambda}(\mu,\sigma^2)$ のとき
    - **平均**：$E[X]=\exp\left(\mu+\frac{\sigma^2}{2}\right)$
    - **分散**：$V[X]=\exp\left(2\mu+\sigma^2\right)\left(\exp(\sigma^2)-1\right)$

## 問題(1)
- **回答**：
$$E[Y]=\exp\left(\mu+\frac{\sigma^2}{2}\right)$$
- **導出**：
$E[Y]=E[\exp(X)]$ を求めるにあたり、正規分布のモーメント母関数を利用して導出する。
$X\sim{N}(\mu,\sigma^2)$ のとき、モーメント母関数は以下となる。
$$
M(t)=E[\exp(tX)]=\exp\left(\mu{t}+\frac{\sigma^2t^2}{2}\right)~…~(i)
$$
ここで $t=1$ とすると、 $(i)$ は以下となる。
$$
M(1)=E[\exp(X)]=\exp\left(\mu+\frac{\sigma^2}{2}\right)
$$

## 問題(2)
- **回答**：
$$E[Y]=\exp\left(2\mu+\sigma^2\right)\left(\exp(\sigma^2)-1\right)$$
- **導出**：
分散の公式 $V[Y]=E[Y^2]-(E[Y])^2$ より、 $E[Y^2]$ について考える。
$E[Y^2]=E[(\exp(X))^2]=E[\exp(2X)]$ となることから、 $(1)$ と同様、正規分布のモーメント母関数を利用して導出する。
$X\sim{N}(\mu,\sigma^2)$ のときのモーメント母関数を用いて、 $t=2$ とすると $(i)$ は以下となる。
$$
E[\exp(2X)]=\exp\left(2\mu+2\sigma^2\right)~…~(ii)
$$
これより、分散 $V[Y]$ を求める。
$$
\begin{align}
V[Y]&=E[Y^2]-\left(E[Y]\right)^2 \\\ &=E[\exp(2X)]-\left(E[\exp(X)]\right)^2 \\\ &=\exp\left(2\mu+2\sigma^2\right)-\left(\exp\left(\mu+\frac{\sigma^2}{2}\right)\right)^2~(\because~(ii),(1)) \\\ &=\exp\left(2\mu+2\sigma^2\right)-\exp\left(2\mu+\sigma^2\right) \\\ &=\exp\left(2\mu+\sigma^2\right)\left(\exp(\sigma^2)-1\right)~(\because~\exp\left(2\mu+\sigma^2\right):共通因数)
\end{align}
$$

## 問題(3)
- **回答**：
$$
\frac{1}{\sqrt{2\pi}\sigma{y}}\exp\left(-\frac{(\log{y}-\mu)^2}{2\sigma^2}\right)
$$
- **導出**：
確率変数 $Y=\exp(X)=g(X)$ の確率密度関数を $h(y)$ とすると、変数変換の公式より以下となる。
$$
h(y)=\frac{f(g^{-1}(y))}{|g'(g^{-1}(y))|}~…~(iii)
$$
ここで $(iii)$ の右辺は、 $\frac{f(x)}{|g'(x)|}$ の $x$ 部分に対し、 $g(x)$ を用いて $y$ に変換したものと考えられるので、まずは分かりやすいよう
$$
\frac{f(x)}{|g'(x)|}~…~(iv)
$$
について考える。
正規分布の確率密度関数 $f(x)=\frac{1}{\sqrt{2\pi}\sigma}\exp\left(-\frac{(x-\mu)^2}{2\sigma^2}\right)$ と $g(x)=\exp(x)$ より、$(iv)$は以下となる。
$$
\begin{align}
\frac{f(x)}{|g'(x)|}=&\frac{1}{\sqrt{2\pi}\sigma}\exp\left(-\frac{(x-\mu)^2}{2\sigma^2}\right)\times\frac{1}{\exp(x)}~…~(v) \\\ &(\because~g'(x)=\exp(x)>0)
\end{align}
$$
ここで $g(x)=exp(x)=y$ 、 $g^{-1}(y)=x=\log{y}$ を $(v)$ に代入すると、$(iii)$の右辺は以下となる。
$$
\begin{align}
\frac{f(g^{-1}(y))}{|g'(g^{-1}(y))|}&=\frac{1}{\sqrt{2\pi}\sigma}\exp\left(-\frac{(\log{y}-\mu)^2}{2\sigma^2}\right)\times\frac{1}{y} \\\ &=\frac{1}{\sqrt{2\pi}\sigma{y}}\exp\left(-\frac{(\log{y}-\mu)^2}{2\sigma^2}\right)
\end{align}
$$
Databricksにおけるインテグレーション

[Databricks integrations \| Databricks on AWS](https://docs.databricks.com/integrations/index.html) [2023/1/13時点]の翻訳です。

:::note warn
本書は抄訳であり内容の正確性を保証するものではありません。正確な内容に関しては原文を参照ください。
:::

Databricksでは、幅広い[データソース](https://qiita.com/taka_yayoi/items/09348912a92a24441c40)、[開発者ツール](https://docs.databricks.com/dev-tools/index.html)、[パートナーソリューション](https://docs.databricks.com/partners/partners.html)のインテグレーションを提供しています。

- [データソース](https://qiita.com/taka_yayoi/items/09348912a92a24441c40): Databricksでは、CSV、[Delta Lake](https://docs.databricks.com/delta/index.html)、Parquet、XML、その他のフォーマットやAmazon S3、GoogleのBigQueryやCloud Storage、Snowflakeなどのデータストレージプロバイダーに対してデータを読み書きすることができます。
- [開発者ツール](https://docs.databricks.com/dev-tools/index.html): Databricksではコードを記述することでDatabricks[クラスター](https://qiita.com/taka_yayoi/items/c5d99cd77fe4bfcf69f0)や[Databricks SQLのウェアハウス](https://qiita.com/taka_yayoi/items/23d7789198c2dcd66381)を通じてデータを操作することができる様々な開発者ツールをサポートしています。これには、IDE、コネクター、ドライバー、IaCプラットフォーム、CI/CDツール、CLI、REST APIおよび認証手段が含まれています。
- [パートナーソリューション](https://docs.databricks.com/partners/partners.html): DatabricksではFivetran、Power BI、Tableauなどの様々なサードパーティソリューションとのインテグレーションを検証しており、多くのケースにおいてローコードやノーコード体験を通じてDatabricksクラスターやSQLウェアハウスを通じてデータを操作することができます。これらのソリューションによって、データ取り込み、データ準備や変換、ビジネスインテリジェンス(BI)、機械学習のような一般的なシナリオを実現することができます。また、Databricksではこれらの検証済みソリューションを、よりクイックかつ簡単にDatabricksクラスターやSQLウェアハウスとインテグレーションできるユーザーインタフェースである[Partner Connect](https://docs.databricks.com/partner-connect/index.html)も提供しています。

[Databricks ReposによるGit連携](https://qiita.com/taka_yayoi/items/b89f199ff0d3a4c16140)もご覧ください。

### Databricks 無料トライアル

[Databricks 無料トライアル](https://databricks.com/jp/try-databricks)
React Hooks Formsでバリデーションを実装してみた

# React Hooks Formsとは

ちゃんとドキュメントをきっちり読み込む。
色々と触ってみる

Reactを用いてフォームを作成しようとするとState の管理が煩雑になりどうしても複雑なコードになってしまう。

どのインプットがエラーの状態で、どんなメッセージを表示する必要があるのかを自分で管理するとなると結構大変。

それがReact Hooks Formを利用することで、その必要がなくなる。

### useStateで管理するとなると？
例えばメールアドレスとパスワードのフォームを作成することをイメージしてみる。

二つのテキストボックスの状態(エラー状態か否か)を管理するステートを定義してかつ、もしそれがエラーならどんなエラーなのかを管理する State をそれぞれ持つ必要がある。

```ts:test.ts
const [email, setEmail] = useState<string>('');
const [password, setPassword] = useState<string>('');

// エラー状態かどうかを管理するEnum
// 0 エラーは起こっていない
// 1 空欄
// ...
const [isEmailError, setIsEmailError] = useState<string>('');
const [isPasswordError, setisPasswordError] = useState<string>('');

```


# React Hooks Formとは？
React Hook Formとは、入力フォームのデータをまとめて簡単に扱えるReact向けのライブラリで。
input要素などに入力した値の取得やバリデーション機能なども備えており、簡単にフォームを実装することができる。

https://react-hook-form.com/

# yupとは

バリデーションのためのライブラリ
JavaScript でスキーマを定義するためのライブラリーである。

オブジェクトを定義するように validation のルールを作っていくことができる。
バリデーションのルールを宣言的に記述することができる。

なくてもreact hooks formの実装は可能だがこのライブラリを用いることでよりわかりやすくルールを記載することができかつ、emailのバリデーションなども用意してくれているみたいなので今回は採用してみた。

# 実際に実装してみる

```ts
// 一部省略
import { useForm } from 'react-hook-form'
import { yupResolver } from '@hookform/resolvers/yup'
import * as yup from 'yup'

const EditForm = (props: Props) => {
  const schema = yup.object<Record<keyof ~~~, yup.AnySchema>>({
    lastName: yup
      .string()
      .required('姓を入力してください')
      .max(30, '30文字以内で入力してください'),
    firstName: yup
      .string()
      .required('名を入力してください')
      .max(30, '30文字以内で入力してください'),
    birthDate: yup.string().required('生年月日を入力してください'),
    sex: yup.number(),
    email: yup
      .string()
      .required('メールアドレスの入力は必須です')
      .email('有効なメールアドレスを入力してください')
  })

  // フォームの定義
  const {
    register,
    handleSubmit,
    formState: { errors },
    setValue,
    getValues,
    watch
  } = useForm<EditProfileEntity>({
    resolver: yupResolver(schema),
    defaultValues: {
      lastName: props.profile.lastName,
      firstName: props.profile.firstName,
      email: props.email,
      ...
    }
  })

return (
    <Box mr={2} ml={2}>
      <Stack>
        {/* メールアドレス入力 */}
        <Stack mt={5}>
          <Typography lineHeight={'2em'} fontWeight="bold">
            メールアドレス
          </Typography>
          <TextField
            {...register('email')}
            fullWidth
            name="email"
            sx={{
              background: '#f0f0f0'
            }}
          />
          <Typography sx={{ color: 'red' }}>{errors.email?.message}</Typography>
          <Typography variant="body2" mt={1} sx={{ fontSize: '0.8rem' }}>
            メールアドレスを変更すると確認メールが送信されます。
          </Typography>
          <Typography variant="body2" sx={{ fontSize: '0.8rem' }}>
            メール内のURLをクリックすると変更が完了します。
          </Typography>
        </Stack>
...
```

このように...registerしていくことで、バリデーションが適用されるようになる。

余談
watchを利用することで特定のフォームの値を監視することもできる。
useStateとwatchの違いはuseStateはあくまで状態の管理で
watchはフォームの値の監視に利用する点。
Oracle Analytics Cloud：接続先のADWにACLを設定する

# はじめに
Public Endpointを持つAutonomous Data Warehouse（**ADW**）に、同じくPublic Endpointを持つOracle Analytics Cloud（**OAC**）からアクセスするケースを想定し、ADWにどのようなアクセス制御リスト（ACL）を設定するべきかを紹介します。
ADWインスタンスがOACインスタンスと同じリージョンにあるかどうかで、指定するアドレスが異なります。
今回は、ADW、OACともに東京リージョンにあるという想定です。

- 参考：[OACインスタンスのPublic IPアドレスの範囲とゲートウェイIPアドレス](https://docs.oracle.com/en/cloud/paas/analytics-cloud/acoci/manage-service-access-and-security.html#GUID-2CDD72A9-6445-491B-BDB9-DBE0ACAF87F3)

# ADWのACLを設定
検索対象のADWのインスタンスの詳細を確認します。
「アクセス制御リスト」の「編集」をクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2342206/eafa8279-9b9f-7d8e-b733-d413a333dad0.png)
CIDRブロックとして「240.0.0.0/4」を指定して、「変更の保存」をクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2342206/c2cf92a7-af3a-8f56-0960-8c600c0de4e2.png)
しばらくすると、変更が適用されます。

:::note info
OACインスタンスがADWインスタンスとは別のリージョンにある場合は、リージョン固有のIPアドレス範囲かゲートウェイIPアドレスを設定します。
例えば、OACインスタンスが大阪リージョンにある場合は、「192.29.242.208/29」または「192.29.242.211」を指定します。
:::

# 相互TLS (mTLS)認証の設定を変更する
必須となっている「相互TLS認証」の設定を編集します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2342206/8e03f4df-7040-e91b-7bcd-6acf48f50674.png)
「相互TLS (mTLS)認証が必要」チェックボックスをオフにして、「変更の保存」をクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2342206/d16ee9ad-789f-e16f-45d4-c4a63888daea.png)
しばらく待つと変更が反映されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2342206/31b4d322-ec8e-4214-6141-407747a502ea.png)

後は、通常通りOACからADWへの「接続」を作って動作確認します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2342206/03597142-2eb0-badd-194b-b40bd7312fa6.png)
Unity学習記録(第1回)

初投稿です．

# 使用教材
__[「Unityによる3Dゲーム開発入門」](https://amzn.asia/d/4e6qnwT)__
大学で借りました．返却期限までに終わらせたいです．

# バージョン
Unity 2021.3.9f1

# 本題
## 第1章
導入とかだったので割愛
## 第2章
オブジェクトは役者，スクリプトが台本という考え方は自分になかった感覚で，以前よりも関係が分かりやすくなった気がします．
### さっそくつまづきポイント
p11~12
シーンに配置したカプセルにPlatform Input Controller というコンポーネントを追加するとあるのですが，探してみても見つかりません．2011年の書籍で，ましてやコンピュータ関連ともなればいろいろ違ってくるのは仕方がないですね．
類似したコンポーネントがないかと探してみましたが，それも見つかりませんでした．Character Controllerとかどうなんだろうと思って調べましたが，どうやらこれキャラクターに使う用の当たり判定みたい，動かす機能は無さげでした．

最終的にこちらのサイトからキャラクターを動かすコードを使わせていただきました．
[「Character Controller」を使ってオブジェクトを動かす【Unity】 | Unishar-ユニシャー](https://miyagame.net/character-controller/)

### オブジェクトの動かし方
[【Unity】アクションゲームにおけるキャラクターの移動方法 – 株式会社ライトコード](https://rightcode.co.jp/blog/information-technology/unity-making-action-game-scratch)
こちらの記事の話です．
オブジェクトを動かすには，大別して
1.Transformの数値をいじる
2.RigidbodyをつけたオブジェクトにAddForceで力を加える
という2つの方法があるようです．
#### 1.Transformいじる系
オブジェクトのTransformの数値そのものを足したり引いたりして移動させます．
物理演算の影響を受けないのが特徴です．
#### 2.物理演算で力を与える系
Rigidbodyなどで物理演算の影響を受けるようにしたオブジェクトに力を加えて移動させます．
教科書の方を優先していて手が付けられていないのですが，公式チュートリアルの _Rall a Ball_ なんかは，AddForce系でやらないと球体の回転処理を別で加えないといけなさそうで面倒なんじゃないかと思います．
AddForceにも力を加えるのか加速度を加えるのかがあるようです．
確かに質量m，加速度a，力Fとして，
 _ma=F_ 
Fが一定ならaが変化しますから，速度や距離も変わりますよね．反対にaが一定なら移動速度や距離は変わらずにFが変わると．Unityさすがだぁ...
ちなみに速度は
変化後の速度v，変化前の速度v0，加速度a，時間t として
v = v0 + (a * t)
x = (v0 * t) + 1/2(a * t^2)
で求められます．
(すみませんTeXわかんないです)
ACFのWYSIWYGエディターをリンクの付け外しだけにするカスタマイズ

今回は、Advanced Custom Fields（アドバンス カスタムフィールド）のテキストエリアに

**「リンクの付け外しだけ」を追加したい！」**

を `WYSIWYG エディター` を使って実現します。

ただ、カスタムフィールドの `WYSIWYGエディター` を使うと、触られたくない無駄なツールがたくさんありますよね。

そこで、ツールバーに表示する機能を制限すれば良いというわけです。

## デフォルトのWYSIWYGには「Full」と「Basic」がある

カスタムフィールドの `WYSIWYGエディター`を作成することで、2つの標準メニュー（「Full」と「Basic」）が表示されるようになっています。

それぞれのツールバーを見ていきましょう。

### WYSIWYGの「Full」

![スクリーンショット 2023-01-16 18.23.24.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2949803/19507164-8867-91de-dcb1-fec47be5d2e0.png)


### WYSIWYGの「Basic」

![スクリーンショット 2023-01-16 18.23.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2949803/b98a958b-2345-770c-e650-9c6961a773fc.png)


## WYSIWYGエディターのツールバーを任意の機能のみ表示する

では、ここから無駄なツールを取り除いていきましょう。

今回は、`functions.php` でリンクの付け外しの機能だけを表示します。

``` php
add_filter('acf/fields/wysiwyg/toolbars', 'original_toolbars');
function original_toolbars($toolbars)
{
	$toolbars['original_toolbar_01'] = array();
	$toolbars['original_toolbar_01'][1] = array('link', 'unlink');
	// $toolbars['original_toolbar_01'][2] = array('〇〇'); 2行目に表示したいツールがある場合
	return $toolbars;
}
```

また、これは何個でも定義できるので、必要に応じて作成してください。

実際にオリジナルのツールバーが追加されました。

![スクリーンショット 2023-01-16 18.24.10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2949803/be1df7ee-c919-8d18-32b6-7d5f60204b7b.png)

エディターの表示も指定したツールだけになっていますね。

![スクリーンショット 2023-01-16 18.24.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2949803/5c833767-7e44-2963-7a6c-ed5b80c421be.png)

ちなみに、以下のメニューが消えないという人は、

![スクリーンショット 2023-01-16 18.24.53.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2949803/3f78181e-2688-466b-ab83-4c2beb35b943.png)

以下の手順で解消します。

1. `Advanced Editor Tools (旧名 TinyMCE Advanced)` プラグインをインストール
2. 旧エディターのクラシックエディター用ツールバーを開く
3. 「エディターメニューを有効化する」のチェックを外す

## ツールバーの定義名一覧

|ツール名|コードでの指定名|
| ---- | ---- |
|太字|bold|
|斜体|italic|
|文字色|forecolor|
|引用|blockquote|
|黒丸リスト|bullist|
|数字リスト|numlist|
|左揃え|aligncenter|
|中央揃え|aligncenter|
|右揃え|alignright|
|両端揃え|alignjustify|
|リンク|link|
|リンク解除|unlink|
|テーブル|table|
|インデントを減らす|outdent|
|インデントを増やす|indent|
|元に戻す|undo|
|やり直す|redo|
|段落|formatselect|
|フォントファミリー|fontselect|
|フォントサイズ|fontsizeselect|
|ツールバー切り替え|wp_adv|
AWS ECS Exec を使ってコンテナの中に入る

## 概要

AWS ECS は何かと難しい。特に厄介なのはコンテナの中に入るのが難しいので、デバッグがしにくいという点だ。ECS Exec という機能を使えばコンテナの中に入ることができることが確認できたので、備忘録的に書き残しておく（いつもググって他の人の記事にばかりお世話になっているのでたまには少し恩返し……）。

とはいえ、良い記事を書いている人たちがすでに大勢いるので、まずはすごく参考になった記事を紹介する。

https://blog.serverworks.co.jp/ecs-exec

とりあえず上の記事を読めば ECS Exec はできるようになるとは思う。ただ、私は私の経験に基づいて少し書いてみる。

感想を言えば、「ECS Exec は1回目は少し大変だが、2回目以降は楽になりそう」という感想。1回目だけ準備しなければならないものがあるからだ。

#### 初回のみ必要なもの:
- ECS Exec の仕組みに対する理解
- AWS CLI のインストール
- Session Manager plugin for the AWS CLI のインストール
- ECS Exec 利用に必要な権限をまとめた IAM Policy の作成

#### ECSサービスを作るたび必要なもの
- ECS タスク定義で上記 IAM Policy をアタッチしたタスクロール（タスク定義ロールではない)を設定
- ECS サービスで ECS Exec を有効化

こんな感じだ。


## 初回のみ必要なもの

ECS Exec の仕組み, AWS CLI, Session Manager Plugin for the AWS CLI のインストールはググって調べてほしい。

#### ECS Exec 利用に必要な権限をまとめた IAM Policy の作成

```json
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "ssmmessages:CreateControlChannel",
                "ssmmessages:CreateDataChannel",
                "ssmmessages:OpenControlChannel",
                "ssmmessages:OpenDataChannel"
            ],
            "Resource": "*"
        }
    ]
}
```

こんな感じの Policy を作って、適当な名前で保存しておく。

## ECSサービスを作るたび必要なもの

#### ECS タスク定義で上記 IAM Policy をアタッチしたタスクロール（タスク定義ロールではない)を設定

タスクロール用のロールを作る。そして上記 IAM Policy をアタッチ。ECS タスク定義でそのロールをタスクロールとして登録しておく。

#### ECS サービスで ECS Exec を有効化

```sh
aws ecs update-service --cluster (クラスター名) --service (サービス名) --enable-execute-command
```
ECSサービスは更新して「デプロイオプション-新しいデプロイの強制」でデプロイしなおす（=タスクを再起動する）。

確認しておくのが重要。

```sh
aws ecs describe-services --cluster (クラスター名) --services (サービス名) | grep enableExecuteCommand
aws ecs describe-services --cluster (クラスター名) --tasks (タスクID) | grep enableExecuteCommand
```
などとして、
```
enableExecuteCommand: true
```
となっていればOK。タスクIDのところは単に16進数の長い文字列(例 `53fb...`)でもよいし、ARN(`arn:aws:ecs:...`) でも良いようだ。

## 接続

```sh
aws ecs execute-command --cluster (クラスター名) --task (タスクID) --container (コンテナ名) --interactive --command "/bin/bash"
```
これでコンテナの中に入れる。

## その他のtips
ECSがうまく動いていないときはそもそもヘルスチェックに失敗していることがある。デバッグして原因を調べたいのにヘルスチェックに失敗してECSがコンテナを停止し続けるとやりにくいので、ヘルスチェックを一時的に止めるのも良いかもしれない。

そういうとき、私はタスク定義の「HealthCheckオプション - コマンド」で `CMD-SHELL, true` として必ずヘルスチェックに成功するようにしている。


 





```
PCを更新したらUbuntu＋Apache＋Gitの設定に悩んだ

Webサイトのデータ管理をノートPC＋Ubuntu＋Apache＋Gitで行っています。
代々バージョンアップを重ねてきた旧PCが動作緩慢になったため、新PCにUbuntu 22.04のクリーンインストールを行い、旧PCの設定を移植しました。
ところが、git pushができません。Apacheのログを確認すると、権限で跳ねられています。新旧PCとも同じOS、同じ設定なのに…。
 ```
"GET /#{gitリポジトリ}/info/refs?service=git-receive-pack HTTP/1.1" 403
 ``` 

あれも効果なしこれも効果なしと悩むこと数時間。Apacheの設定に「SetEnv REMOTE_USER=$REDIRECT_REMOTE_USER」を追加したら解決しました。
 ``` 
<VirtualHost *:80>
    SetEnv GIT_PROJECT_ROOT /srv/git
    SetEnv GIT_HTTP_EXPORT_ALL
    SetEnv REMOTE_USER=$REDIRECT_REMOTE_USER #この行を追加したら動作した！
    ScriptAlias /git /usr/lib/git-core/git-http-backend/

    <Directory "/usr/lib/git-core">
        Options +ExecCGI -MultiViews +SymLinksIfOwnerMatch
        AllowOverride None
        Require all granted
    </Directory>
</VirtualHost>
 ``` 
同じバージョンのOSでもバージョンアップの経緯により動作が変わるなんてことがあるんですね。
Renesas RAマイコンを使ってみよう(5)～UARTとスイッチを使ってみよう～2

__Renesas RAマイコンを使ってみよう(4)～UARTを使ってみよう～__  の続きです。
https://qiita.com/usashirou/items/76d4a441253a25185adb

スイッチを押したらUARTで送信するプログラムにしてみましょう。
__R_IOPORT_PinRead__ によりLED及びURATの送信をするプログラムになります。
# 修正部分
以下のように修正します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/e8f3f171-902f-8e67-815d-99e9ed1a3919.png)

    R_IOPORT_PinRead
により __R_SCI_UART_Write__ を送信しています。
# プログラム
```
void hal_entry(void)
{
    uint8_t data[] = "SW1\n\r";
    R_SCI_UART_Open(&g_uart0_ctrl, &g_uart0_cfg);

    /* TODO: add your own code here */
    while(1){
        bsp_io_level_t SW1_status;
             R_IOPORT_PinRead(&g_ioport_ctrl, SW1, &SW1_status);
                    if(SW1_status){
                        R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_HIGH );
                    }else{
                        R_SCI_UART_Write(&g_uart0_ctrl, data, sizeof(data));
                        R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_LOW );
                    }
         R_BSP_SoftwareDelay(3, BSP_DELAY_UNITS_MILLISECONDS);
    }
}
```
# UARTの受信に応じて動作するプログラム
次に、UARTで受信した内容を基にLEDを点灯させてみます。
最初に __R_SCI_UART_Read__ によりUARTを読み込みます。
# GPIO Read
__Developer Assistance__ を開いて __Call R_SCI_UART_Read__ を探します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/72758adc-48d0-97b0-dd37-03cd3ee14e44.png)
## Case文
読み込んだ __UART__ に応じてcase文を構成しました。
今回は、文字列として１，２，それ以外の場合にLEDの点灯方法が変わるようになっています。
# プログラム
```
void hal_entry(void)
{
    uint8_t msg[] ="Hello Renesas RA \r\n";
    uint8_t rev;

     R_SCI_UART_Open(&g_uart0_ctrl, &g_uart0_cfg);
     R_SCI_UART_Write(&g_uart0_ctrl, msg, sizeof(msg));
     
  while(1){
      R_SCI_UART_Read(&g_uart0_ctrl, &rev, 1000);
            switch(rev){
            case '1':
                R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_HIGH );
                R_IOPORT_PinWrite(&g_ioport_ctrl, LED2_PMOD1_IRQ,BSP_IO_LEVEL_LOW );

                break;
            case '2':
                R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_LOW );
                R_IOPORT_PinWrite(&g_ioport_ctrl, LED2_PMOD1_IRQ,BSP_IO_LEVEL_HIGH );

                break;
            default:
                R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_LOW );
                R_IOPORT_PinWrite(&g_ioport_ctrl, LED2_PMOD1_IRQ,BSP_IO_LEVEL_LOW );
                break;
            }
      }
}
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/552c3ad3-8f09-d373-039d-190047c482f3.png)
# 出力の様子
![スクリーンショット](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/11c20745-e7d3-a673-4cf5-56fd28528a98.png)
Renesas RAマイコンを使ってみよう(3)～スイッチを使ってみよう～

RAマイコンを使ってみよう～Lチカ編～の続きです。

https://qiita.com/usashirou/items/33a676f4c63220b9f910

今回は、スイッチを使ってみましょう。
# ピン設定を確認する
__P205__ がスイッチに繋がっています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/c313145a-8ab0-32f8-ad3f-2f57db60042a.png)
__Configuration__ を見ると __SW1__ になっています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/85745be2-f24a-ca8d-8fde-c351a39ac732.png)
__Developer Assistance__ から __R_IOPORT_PinRead__ を探しプログラムに貼り付けます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/1eb2a3df-b071-68cf-46ee-1bd5199a7138.png)
__R_IOPORT_PinRead(&g_ioport_ctrl, SW1, &SW1_status)__ とプログラムを修正します。
ただし __value__ が規定されていません。
__bsp_io_level_t SW1_status__ を追加します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/ce0ad083-48ae-127f-4eb8-234500626410.png)
次に、 __Status__ に応じてプログラムを構成します。
__SW1__ の __Status__ に応じてLEDが点滅するようにします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/e649e298-cf35-085d-c493-d07aaff8ae93.png)
__sw1__ と入力すると補完で __sw1_status__ が出てきます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/45c66519-51db-f322-6aa5-40e60fd18eb7.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/ba5baa9f-ee07-f40a-0dff-9b3eb4821fcc.png)

```
void hal_entry(void)
{
    /* TODO: add your own code here */
   while(1){
       bsp_io_level_t SW1_status;
        R_IOPORT_PinRead(&g_ioport_ctrl, SW1, &SW1_status);
               if(SW1_status){
                   R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_HIGH );
               }else{
                   R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_LOW );
               }
    R_BSP_SoftwareDelay(3, BSP_DELAY_UNITS_MILLISECONDS);
    }
}
```
# LED2の追加
今回も　__LED2__ を修正しました。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/285344/1242ee58-4d69-3e40-9797-7bb7709ead2c.png)
# プログラム
```
void hal_entry(void)
{
    /* TODO: add your own code here */
   while(1){

       bsp_io_level_t SW1_status;
        R_IOPORT_PinRead(&g_ioport_ctrl, SW1, &SW1_status);
               if(SW1_status){
                   R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_HIGH );
                   R_IOPORT_PinWrite(&g_ioport_ctrl, LED2,BSP_IO_LEVEL_LOW );

               }else{
                   R_IOPORT_PinWrite(&g_ioport_ctrl, LED1,BSP_IO_LEVEL_LOW );
                   R_IOPORT_PinWrite(&g_ioport_ctrl, LED2,BSP_IO_LEVEL_HIGH );
               }
    R_BSP_SoftwareDelay(3, BSP_DELAY_UNITS_MILLISECONDS);
    }
}
```
未経験からエンジニアになる：サーバー構成を知ろう！

未経験からエンジニアになりたい人は、プログラミングから始める人が多いと思いますが、
エンジニアの仕事は、プログラミングだけではありません。そして、プログラミングだけでは、エンジニアになれません。同時にプログラミングが苦手でも、システム構成や開発の流れを理解するとエンジニアに近づきます！
今回はサーバー構成について調べてみましょう！

![インスタスライド_202301021.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/23130/40380d78-316a-2d0a-86b9-1a716be35f0a.gif)

# サーバーとは
プログラミングをしてテストがOKであれば本番サーバーにソースをデプロイします。
サーバーの構成って知ってますか？

# 簡単なイメージ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/23130/77b0b319-f224-1c73-485d-49dc75fa9bbb.png)

# Webサーバー
Webサーバーは、障害対応のため２台以上が一般的です。
１台が壊れても別のサーバーで応答できる様になってます。
２台以上で動くのでローカルでファイルを扱う様なプログラムはちゃんと動作しませんので注意しましょう

# ロードバランサー
Webサーバーが２台以上のため、その前でロードバランサーが２台以上のWebサーバーにリクエストを割り振ります。
割り振り方は色々と設定があります。

# F/W
FireWall聞いた事は無いですか？
セキュリティ上サーバーを外部からの攻撃から守るためのサーバー、仕組みです。

# DBサーバー
Databaseサーバーです
MySQLやPostgreSQL等のデータベースが置かれるサーバーです。
セキュリティ上Webサーバーとは別に奥に置かれるサーバーです。

# キャッシュサーバー
データベースへのアクセスは、少し遅いことがあります。
そのため使われるのがキャッシュサーバーです
データをメモリ上に保管して、素早くデータを返します

# まとめ
プログラムが動くには、色々な機能のサーバーのまとまりが必要です。
プログラムが動く環境がどうなっているのかはプログラミング前に確認しときましょう

# 最後に
未経験の皆さん、若手エンジニアの皆さん、勉強方法について悩みがあればなんでも気軽に質問して下さい！
これからも記事を書いていきますので、モチベーションアップのためフォロー、イイねお願いします。
Inpaintingモデル DeepFillv2の使い方

# 方法

https://github.com/csqiangwen/DeepFillv2_Pytorch

### インストール

```bash
git clone https://github.com/csqiangwen/DeepFillv2_Pytorch.git
cd DeepFillv2_Pytorch
pip install imgcrop
gdown https://drive.google.com/u/0/uc?id=1uMghKl883-9hDLhSiI8lRbHCzCmmRwV-
```

### 推論

```bash
python3 test.py --baseroot './test_data/' --baseroot_mask './test_data_mask/' --results_path './results' --gan_type 'WGAN' --gpu_ids '1' --epoch 40 --batch_size 1 --num_workers 8 --pad_type 'zero' --activation 'elu' --norm 'none'
```

![スクリーンショット 2023-01-17 6.03.58.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/235259/03e4227d-ccfe-0cd5-4655-808294773ca5.png)
![07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/235259/b0bff068-6bc8-1ed0-b451-5695a38b28c6.png)
![a7d7577e-b625-4668-b030-6c9215ed1f74.jpeg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/235259/f35e59cb-9e6c-341c-3042-df8ac8c198a6.jpeg)
🐣
****
フリーランスエンジニアです。
お仕事のご相談こちらまで
rockyshikoku@gmail.com

機械学習、ARアプリ（Web/iOS）を作っています。
機械学習／AR関連の情報を発信しています。

[Twitter](https://twitter.com/JackdeS11)
[Medium](https://medium.com/@rockyshikoku)
[GitHub](https://github.com/john-rocky)
AffinityDesignerでエクスポートしたsvgファイルをAndroid Studioでインポートしたときに崩れてしまった場合の対処法

# はじめに

僕は普段Androidアプリのアイコンを作成するときは、Affinity Designerを使用します。

https://affinity.serif.com/ja-jp/designer/

しかし、Affinity DesignerでエクスポートしたSVGをAndroid Studioでインポートしたときに度々デザインが崩れてしまう現象が発生していました。

今回は、次のアイコンを作成したときに発生した問題について解決方法が見つかったのでまとめていきたいと思います。

![4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/577119/61c39c57-3548-10c0-1f00-1eaec75390f7.png)


# Affinity Designerの問題

まずは、エクスポートした上記のSVGファイルをAndroid Studioで読み込んだときの画面をご覧ください。

![1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/577119/2d71a3e5-bfd1-37d8-0f10-ba16192292da.png)

お分かりの通り、カーブしている部分の丸みがなくなっていて、白い部分が重なってしまい表示が崩れていることがわかります。

# 解決方法

実は、Affinity Designer以外のデザインツールとしてCanvaも普段使用しています。

https://www.canva.com/

このCanvaでアイコンと同じサイズでファイルを作成して、作成したsvgをインポートして配置します。

それを、再度**SVG**としてエクスポートします。

![2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/577119/a5bd2ab2-a51a-b04c-f9d5-3e2baaaf1089.png)

そして、CanvaでエクスポートしたSVGファイルをAndroid Studioでインポートします。

![3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/577119/6eeb358f-a5ae-ab13-5998-5935b76a380d.png)

じゃじゃーん！！！

なんと、先ほどの表示の崩れが修正されました！

# まとめ

もし、僕と同じようにAffinity DesignerとCanvaを利用している開発者の方で、やっぱりAdobe Illustratorを買わないといけないのか・・・という悩みを抱えている方は、一度上記の方法を試してみることをおすすめします！
generative-inpainting-pytorchをつかう

# 方法

### インストール

```bash
git clone https://github.com/daa233/generative-inpainting-pytorch.git
cd generative-inpainting-pytorch
pip install pyyaml==5.4.1
```

### 推論

```bash
python test_single.py --checkpoint_path path_to_pretrained_model_dir --image your_image.png --mask examples/center_mask_256.png	--output examples/output.png
```

![inin.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/235259/210d61e4-6e4b-731c-727c-732b37707c29.png) ![f23cf4a0-619e-4b47-893e-4b9cb22d481b.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/235259/553a39c6-c79c-8c87-826f-f5e38b706952.png)

🐣
****
フリーランスエンジニアです。
お仕事のご相談こちらまで
rockyshikoku@gmail.com

機械学習、ARアプリ（Web/iOS）を作っています。
機械学習／AR関連の情報を発信しています。

[Twitter](https://twitter.com/JackdeS11)
[Medium](https://medium.com/@rockyshikoku)
[GitHub](https://github.com/john-rocky)
2023/1/17主にITとかセキュリティの記事

知っておきたいフィッシング、スミッシング、ビッシングの違い(1/15)
https://news.mynavi.jp/techplus/article/20230115-2559218/

Windows 10のブルースクリーン問題を解消　Windows 7／8.1に最後の「Windows Update」(1/15)
https://news.yahoo.co.jp/articles/07314a255c1314e8c762bc8536c6195045852919?source=rss

サイバー脅迫に「交渉人」　身代金減額、委任リスクも(1/15)
https://www.nikkei.com/article/DGXZQOUC249070U2A021C2000000/

国内企業の4分の1が被害に！深刻化するランサムウェアの手口と感染経路(1/15)
https://dime.jp/genre/1526228/

サポート詐欺に注意！！警告が表示されても冷静に 警視庁サイバーセキュリティ対策本部(1/15)
https://www.risktaisaku.com/articles/-/75869

米国はサイバー攻撃対策の支援を理由にスパイ活動を行い得る＝仏紙(1/14)
https://sputniknews.jp/20230114/14576219.html

アルゴリズムは開示すべき!? 食べログ裁判から考えるインターネット業界の新潮流(1/15)
https://news.yahoo.co.jp/articles/398cfe5645256fe567a28aaba45f524a0942b18d?source=rss

役に立たなかった資格は？「TOEIC 765点 は中途半端で求人通過せず」「ITパスポート持ってたけど……」(1/15)
https://news.nicovideo.jp/watch/nw11961729

これなしでITは成り立たない、アルゴリズムの基礎「探索」を学ぶ(1/16)
https://xtech.nikkei.com/atcl/nxt/column/18/02296/121600001/

AWSで疎結合のフロント系を実装　独自の大規模アジャイル体制を構築 KDDI(1/16)
https://xtech.nikkei.com/atcl/nxt/mag/nc/18/020600004/011100122/

クラウド最適化が脚光　23年の注目IT基盤(1/16)
https://xtech.nikkei.com/atcl/nxt/mag/nc/18/020600014/011000134/

適応学習（Adaptive Learning）(1/16)
https://xtech.nikkei.com/atcl/nxt/mag/nc/18/020600009/011000132/

情シスの「やめられる仕事」「減らせる仕事」5選、今年こそ挑戦の余力つくろう(1/16)
https://xtech.nikkei.com/atcl/nxt/column/18/00205/010600080/

ネット銀行と地銀による異色のタッグが実現、ソニー銀と千葉銀が見据える未来とは(1/16)
https://xtech.nikkei.com/atcl/nxt/column/18/00001/07495/
[Streamlit Cloud] デプロイ時にパッケージinstallできないバグ


[streamlit](https://streamlit.io/)を最近知ったのですが手軽にデータ処理をしてそのままUIに乗っけたいときに重宝しています。

今回はstreamlitで作ったアプリを公開したく Streamlit Cloudにデプロイしようとしたときにパッケージがinstallできないバグに遭遇したのでその解決法です。
＊パッケージ管理はanacondaを使用していました。

<b>環境</b>
conda 4.11.0
python 3.9

# 解決法
先に結論を言うとconda経由のinstallは諦めてpipに変えました。
`pip list --format=freeze > requirements.txt`

# 何をしたか
## ①`conda list -e > requirements.txt`
一番最初は上記のコマンドで作成したrequirements.txtをあげていました。

これはconda用の環境のようです。streamlit cloudではrequirements.txtはpipでinstallするのでエラーが起きてしまいました

#### エラー内容
```bash
ERROR: Invalid requirement: '_ipyw_jlab_nb_ext_conf=0.1.0=py38_0' (from line 4 of /app/chem_app/requirements.txt)

Hint: = is not a valid operator. Did you mean == ?
```

## ②`conda env export > environment.yml`
condaでinstallしたい場合はenvironment.ymlで出力すれば良いとのこと。

https://discuss.streamlit.io/t/managing-your-streamlit-dependencies-using-conda/12346/11

packageの解決ができず断念。
#### エラー内容
```bash
Collecting package metadata (repodata.json): ...working... [日付] done
Solving environment: ...working... [日付] failed
```

## ③`pip freeze > requirements.txt`
condaで一通り触って無理だったので潔く諦めました。
＊conda経由のinstallでエラーが出るissueも散見できます。

pipで依存パッケージを入れた後にrequirements.txtに出力してあげました。
installで普通にエラー。
requirements.txtを確認するとバージョンを出力してほしいところに`@file`みたいな記述が、、
https://teratail.com/questions/272968

## ④`pip list --format=freeze > requirements.txt`
先ほどのteratailで触れてある通りformatを指定してみます。
requirements.txtから`@file`が削除され無事versionが出力されました。

installまでは成功したのですが謎のエラーに苦しめられ起動できない。もう一歩
#### エラー内容
```
ResolvePackageNotFound: 
 × Building wheel for pycairo (pyproject.toml) did not run successfully.
  │ exit code: 1
  ╰─> [12 lines of output]
      running bdist_wheel
      running build
      running build_py
      creating build
      creating build/lib.linux-x86_64-cpython-39
      creating build/lib.linux-x86_64-cpython-39/cairo
      copying cairo/__init__.py -> build/lib.linux-x86_64-cpython-39/cairo
      copying cairo/__init__.pyi -> build/lib.linux-x86_64-cpython-39/cairo
      copying cairo/py.typed -> build/lib.linux-x86_64-cpython-39/cairo
      running build_ext
      'pkg-config' not found.
      Command ['pkg-config', '--print-errors', '--exists', 'cairo >= 1.15.10']
      [end of output]
  note: This error originates from a subprocess, and is likely not a problem with pip.
  ERROR: Failed building wheel for pycairo
```

## ⑤`pip list --format=freeze > requirements.txt`
潔くconda環境を作り直し、全てpip経由で入れました。

無事動いた
```bash
[] 🐍 Python dependencies were installed from /app/[app]/requirements.txt using pip.
[] 📦 Processed dependencies!
```
actを使ってGitHub Actionsをローカルで実行してみる

# actとは

- GitHub Actionsをローカルで実行するためのツール
- これにより、いちいちGitHub上でなくても手元環境である程度の検証が可能になる
- とはいえ、GitHub Actionsを完全に再現するものではないため注意
- GitHubリポジトリ: https://github.com/nektos/act

# インストール

```bash
$ brew install act
```

# 初回実行

- 初回実行時はコンテナイメージのスペックをMicro/Medium/Largeの3種類から選ぶよう促される
- いずれにせよ実行環境はUbuntuで、GitHub ActionsのようにmacOSやWindowsは選択できない
- 詳細: https://github.com/nektos/act#runners

```bash
$ act
```

- 初回実行すると `~/.actrc` に設定が保存される

```~/.actrc
-P ubuntu-latest=catthehacker/ubuntu:act-latest
-P ubuntu-22.04=catthehacker/ubuntu:act-22.04
-P ubuntu-20.04=catthehacker/ubuntu:act-20.04
-P ubuntu-18.04=catthehacker/ubuntu:act-18.04
```

# 環境変数/シークレットの設定

- GitHub Actionsの設定で環境変数やシークレットを使用している場合に必要な設定
- 実行時にオプションとして渡すことも可能だが、あらかじめ設定に書いておくと便利
- 詳細
    - https://github.com/nektos/act#secrets
    - https://github.com/nektos/act#configuration

```~/.actrc
-P ubuntu-latest=catthehacker/ubuntu:act-latest
-P ubuntu-22.04=catthehacker/ubuntu:act-22.04
-P ubuntu-20.04=catthehacker/ubuntu:act-20.04
-P ubuntu-18.04=catthehacker/ubuntu:act-18.04
--secret-file .act.secrets
--env-file .act.env
```

```~/.act.secrets
GITHUB_TOKEN=XXXXXXXXXX
```

```~/.act.env
FOO=foo
BAR=bar
BAZ=baz
```

- GitHub Actionsの場合、GITHUB_TOKENを自動で読み込んでくれるが、actの場合はそうはいかないので、事前にPAT(Personal access tokens)を生成しておく必要がある
- 最低でもrepoの権限が必要らしい
- 詳細: https://docs.github.com/ja/authentication/keeping-your-account-and-data-secure/creating-a-personal-access-token

# その他コマンド

```bash
# 一覧の表示
$ act -l
Stage  Job ID  Job name  Workflow name  Workflow file  Events
0      build   build     Build          main.yml       push  

# ドライラン
$ act -n
```
VPN不要でヨーロッパからYahoo Newsを見る方法

<b>背景</b>
EUのデータ保護の関係で2022年4月6日からヨーロッパでYahoo Newsが見れなくなりました。
VPNを使うのが無難な解決策なのですが、お金をかけたくないので他に方法がないか試しました。
その結果、VPN不要でヨーロッパからyahoo newsを見る方法を発見しました。

<b>方法</b>
Google Colaboratoryからスクレイピングする。

終わり
ABC285 C問題：ゼロを使わないN進法についてのメモ

https://atcoder.jp/contests/abc285/tasks/abc285_c

上の問題で、表計算ソフトの列番号によくある `A`, `B`, … , `Z`, `AA`, … といった文字列が何番目を指すのかを問われた。

何となく `A` → 1, `B` → 2, … , `Z` → 26 と「*ゼロを抜いて*各文字に番号を振った」うえで「普通の26進法と同じ計算をした」ところ正答できた（試していたらできそうに見えただけで、何も証明していない）。しかし、普通は十進法なら 0 ～ 9 というようにゼロを入れて N は入れないはずで、この解き方は**N進法のルールを破ってしまっている**気がする。

```ruby:convert.rb
def str2num(str)  # str = "BRUTMHYHIIZP"
	digits = str.bytes.map { |b| b - 0x40 }  #=> [2, 18, 21, 20, 13, 8, 25, 8, 9, 9, 26, 16]
	digits.inject(0) { |s, d| s * 26 + d }   #=> 10000000000000000
end

# おまけ：逆方向の変換
def num2str(num)  # num = 10000000000000000
	digits = []
	while num > 0
		num, d = (num - 1).divmod(26)
		digits << d + 1
	end
	digits = digits.reverse                 #=> [2, 18, 21, 20, 13, 8, 25, 8, 9, 9, 26, 16]
	digits.map { |d| d + 0x40 }.pack("C*")  #=> "BRUTMHYHIIZP"
end
```

---

調べたところ、各桁で 0 を使わず 1 ～ N を割り当てるようなN進法（位取り記数法）は **"bijective base-N numeration"** としてきちんとあるらしい。

https://en.wikipedia.org/wiki/Bijective_numeration

* 任意の自然数と文字列とが1対1対応する。（だから名前に「全単射」とある）
	* それに対して通常のN進法だと、[ゼロ埋め](https://ja.wikipedia.org/wiki/ゼロパディング)しても同じ数値になるため1対1でない。
	* 同じ最大桁数であれば通常のN進法より多くの数値を表せる。
	* 空文字列を認めれば、数値のゼロも文字列で表せる。
* **文字列から数値への変換は、通常のN進法と同じ式。**
	* したがって表記中に 0 や N を含まない数は、通常版でも全単射版でも同じ数値を表す。
	* 数値から文字列への変換も、通常版の方法を僅かに変更すればできる。
* 加算や乗算も、通常のN進法と同じ要領で筆算できる。（繰り上がりの処理でゼロの桁を作らないようにだけ注意）

証明にはならないが、十進法で実際に試してみれば妥当な雰囲気が掴める。

---

冒頭の問題が26進法でいけそうに見えたのは、 `Z` を含んでいないものは本当に通常の26進法と数値が一致するからかもしれない。
[Swift UI]正方形のカメラ画面を作成する方法

結論から書くとカメラサイズを指定してあげればOKです

<img width="400" alt="IMG_81FB47237FC0-1.jpeg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/494487/6f78fdb6-a1b4-3256-13ed-d6df6403490e.jpeg">

画面が横になってるのは横画面のアプリを作ってるからです(コメントアウトして外してあります)


### まずはinfo.plistでこちらを追加
カメラの権限です

    Privacy - Camera Usage Description

そしてコードはこちら（コピペでok）

    import SwiftUI
    import AVFoundation

    struct ContentView: View {
        var body: some View {
      
            VStack{
                CameraView()
            }
            .frame(width: 300, height: 300)
            .background(Color.orange)
        }
    }

    struct CameraView: UIViewRepresentable {
        func makeUIView(context: Context) -> UIView { BaseCameraView() }
        func updateUIView(_ uiView: UIViewType, context: Context) {}
    }

    class BaseCameraView: UIView {
        
        override func layoutSubviews() {
            super.layoutSubviews()
            _ = initCaptureSession
            (layer.sublayers?.first as? AVCaptureVideoPreviewLayer)?.frame = frame

        }

        lazy var initCaptureSession: Void = {
            guard let device = AVCaptureDevice.DiscoverySession(
                deviceTypes: [.builtInWideAngleCamera],
                mediaType: .video,
                position: .unspecified)
                .devices.first(where: { $0.position == .front }),
            let input = try? AVCaptureDeviceInput(device: device) else { return }
            let session = AVCaptureSession()
            session.addInput(input)
            session.startRunning()
            let previewLayer = AVCaptureVideoPreviewLayer(session: session)
            previewLayer.videoGravity = .resizeAspectFill //←これが必要
    //        previewLayer.connection?.videoOrientation = .landscapeRight
            layer.insertSublayer(previewLayer, at: 100)


        }()
    }

カメラのサイズを正方形にする必要がありどうやってもできなくて詰まってたんですが、なんとか記事を見つけて修正したらできました

swift ui カメラ 正方形でググってもそれっぽい記事が出てこなくてイライラしたのでそういう思いをしてほしくないなと思い忘備録を残します

どなたかの参考になれば幸いです
Webを支える技術 アウトプット メモ

# 第一部 Web概論 (第一章 Webとは何か? ) アウトプットメモ

## Webはすべての基盤である

現在のコンピュータにとって、最も大切なソフトウェアはブラウザである。

私たちは、ブラウザを通じてインターネットの向こう側にあるWebサーバーとやりとりして、ショッピングサイトで買い物をしたり、地図や乗り換え情報を得たりしている

Webは現在の生活に根付いているため、すべての基盤であるといえる

※10年前であれば、最も大切なソフトウェアはワープロ(ワードプロセッサー)や基幹業務のソフトウェア

## Webは様々な用途で使われている

※同じWebの技術でも、その用途は多岐にわたる

### Webサイト

最も身近な例
ex) Amazon、Google、Wikipedia、SNS...ect.

Webサイトのシステム構成は、PCベースのUNIX 1台のケースから、何千・何万ものサーバーを繋ぎわせたケースまで、多くのバリエーションがある

↑

Webサイトの裏側までクライアントが意識しないで済むことが、Webの大きな特徴といえる

Webは多様な種類のブラウザに加え、多くのソフトウェアやハードウェアから利用されている
ex) 携帯電話、ゲーム機、そのほかデバイス...ect.

### UI

意外に思うかもしれないが、リモコンやハードウェアの限定されたボタンで設定するよりもPCのキーボードで操作したほうが効率的のため

別例) htmlでのヘルプ記述
windowsにはhtmlヘルプと呼ばれる機構があり、htmlベースでソフトウェアやハードウェアのヘルプが作成可能

写真管理ソフトが配布用に画像にリンクしたHTMLを生成するのものWeb技術をインターフェース面で応用した例

このような応用がされるのは、HTMLが記述・編集しやすいことと、多様な環境でブラウザが利用できるから

### Web API

- UIとしてのWeb → 人間向けのインターフェース
- APIとしてのWeb(Web API) → プログラム向けのインターフェース

データフォーマットには、XMLやJSONなどのプログラムが解釈・処理しやすいものが用いられる

## Webは3つの技術に支えられ、2つの側面を持つ

### HTTP、URI、HTML

Webを支える最も基本な技術

- URI → ショッピングサイトの商品、学術論文、動作サイトに投稿されて動画でも、世界中の情報を示せる
- HTML → URIの情報を表現する文章フォーマット
- HTTP → URIの情報を取得したり、発注したりする

上記はシンプルな技術
このシンプルさでWebは様々な応用を可能としている

HTTP1.1が定義しているメソッドは8だけ
| メソッド  | 説明 |
| :------------- | :------------- |
| GET | 最も一般的に使用されるメソッド<br/>ブラウザはサーバに対してページの取得を要求  |
| HEAD | ヘッダのみの情報を要求<br/>サーバは GET メソッドと HEAD メソッドは必ずサポートしなければならない |
| POST | CGI でよく使用されるメソッド<br/>method="POSTを指定したフォームに入力したデータをサーバに転送する際に使用|
| PUT | ファイルをサーバにアップロードする際に使用 |
| DELETE | 指定したリソースを削除することをサーバに要求 |
| CONNECT | プロキシサーバを経由して SSL 通信する際などに使用 |
| OPTIONS | サーバがサポートしているメソッドやオプションを調べる際に使用 |
| TRACE | HTTP要求がどのプロキシサーバを経由して送信されるかなど、HTTP の動作をトレースする際に使用<br/>このメッセージを受け取った最後のサーバは、要求メッセージに含まれるエンティティ（通常はヘッダ＋メッセージボディ）をそのまま返す|



URIは紙の広告に記載できるくらい短い文字列
```HTML:URI
https://www.example.com/
```

HTMLはXMLをベースとした汎用文章フォーマット
```XML:XML
<?xml version='1.0' encoding='UTF-8'?>
<doc>
	<p>Hello World!!</p>
</doc>
```
```HTML:HTML
<html>
	<head>
		<title>HTML文書の例</title>
	</head>
	<body>
		<p>Hello World</p>
	</body>
</html>
```

URI、HTML、HTTPに支えられたWebは、情報システムとしてみると**ハイパーメディアシステム**と**分散システム**の二つの側面を持つ

#### ハイパーメディアシステム
テキスト、画像、音声、映像などの様々なメディアをハイパーリンクで結び付けて構成したシステム

ハイパーメディア以前のメディア
ex) 書籍、映画
- 線形的に先頭から読んだり、視聴したりする

ハイパーメディア
ex) YouTube
- 非線形的にユーザ自身がリンクを選択し、情報を取得する

ハイパーリンク(リンク) → 情報同士を結びつける機構
ユーザが情報から別の情報へと自由に参照できるようになる

### 分散システム
複数のコンピュータを組み合わせて処理を分散させる仕組み

一台のコンピュータで実行するよりも効率的に処理が可能

複数のコンピュータ上に存在するデータを一元的に扱ったり、一台のコンピュータでは扱え切れない膨大なデータを操作したりできる

Webは世界中に配置されたサーバに、世界中のブラウザがアクセスする分散システム

分散システムとしてのWebの特徴はシンプルな点
プロトコルがシンプルだからこそ、大規模なシステムが実現できている
Twitter API：tweepyを使わずPythonのrequestsでツイートを検索する

tweepyを使わず、Pythonの標準モジュールであるrequestsを使って直接Twitter APIのエンドポイントに接続してツイートを取得する方法を紹介します。

個人的には、tweepyでラップされている書き方よりも、こちらの方が公式ドキュメントに即して書けるのでおすすめです。

今回のツイートを検索するエンドポイントに関する公式ドキュメントは[こちら](https://developer.twitter.com/en/docs/twitter-api/tweets/search/api-reference/get-tweets-search-recent)です。

なお、この記事では、Twitter APIがすでに使える状態になっていることを想定しています。

## 必要なモジュールをインポート

```python
from datetime import datetime #日付データを扱う
import pandas as pd #DataFrameを扱う
import requests #HTTP通信をする
import json #JSONデータを使用する
import time #時間を扱う
```

## 検索条件を指定

- 検索キーワードの作り方は[こちら](https://developer.twitter.com/en/docs/twitter-api/tweets/search/integrate/build-a-query#build)を参照してください。
- 期間の`start_time`は最大でも1週間前を指定してください。Twitter APIの仕様なのでしょうがないです。ちなみにこれ以上検索したい場合はAcademic Research Accessを申請してフルアーカイブサーチを使う必要があります。

```python
# 検索キーワード
key_word="Python OR python -is:retweet"  

# 期間
start_time="2023-01-15T00:00:00.000Z"
end_time="2023-01-16T00:00:00.000Z"
```

## Bearer Tokenを指定
APIの認証（OAtuth 2.0認証）に必要となるトークンです。Twitter Developer Portalより取得できます。
```python
bearer_token = "" 
```
ここまでは各自で入力が必要ですが、この後はコピペでいけます。


## リクエストを送るのに必要な情報を整理
- `search_url`が今回仕様するエンドポイントです。
- `max_results`は100が最大です。
- `tweet.fields`にはツイートの内容以外に取得したい情報を指定します。詳しくは公式ドキュメント参照。

```python
search_url = "https://api.twitter.com/2/tweets/search/recent"
headers={'Authorization':f"Bearer {bearer_token}"}
query_params = {
    "query":key_word,
    "start_time":start_time,
    "end_time":end_time,
    "max_results":100,
    "tweet.fields": ["created_at,author_id"],
}
```

## APIのリクエストを送って結果を取得する
いよいよリクエストを送っていきます。

Twitter APIは複数のページにわたって検索結果がまとまっているのですが、最初のレスポンスではその内最初のページ（`max_result`で指定した100件以内分）しか返してくれません。
次のページを取得するには、レスポンス内にある`next_token`をパラメータに含めて再度リクエストを送り直す必要があります。
以下ではその処理をWhile文で実装しています。

また、Twitter APIは15分で150requestsの制限があり、それを超えるとエラーを返してくるので、それを防ぐために`count`でリクエスト回数を記録して、140に達したら15分ほど休ませています。

```python
data_list = [] #ここに結果を格納していきます
count = 0 #リクエストを何回送ったか
next_token = None
while True:  
    query_params["next_token"] = next_token
    response = requests.get(search_url, headers=headers, params=query_params)
    if response.status_code != 200: #エラーの時に詳細を表示
        raise Exception(response.status_code, response.text) 
    res_json = response.json()
    data_list.extend(res_json["data"])
    print(res_json["meta"])  
    if len(res_json["meta"]) == 3: #next_tokenがなくなったら
        break
    else:
        next_token = res_json["meta"]["next_token"]
    count += 1   
    
    if count == 140: #150でerror
        print('waiting')
        time.sleep(60 * 15)
        count = 0
```
## 結果をDataFrameに変換してcsvで保存

カレントディレクトリに検索語と期間の名前がついたcsvファイルで保存されます。

要らなそうな列を落として日付の昇順に直しています。
Twitter APIは直近からさかのぼって取得していくのでデフォルトだと降順になっています。
```python
df = pd.DataFrame(data_list).drop(columns=["edit_history_tweet_ids","id"]).sort_values("created_at")
period = f"{pd.to_datetime(start_time).strftime('%Y%m%d')}_{pd.to_datetime(end_time).strftime('%Y%m%d')}"
filename = f"./{key_word}_{period}.csv"
filename = filename.replace(' ','')
df.to_csv(filename)
```
FLAN-T5-XXL を 3090 で動かす

https://huggingface.co/google/flan-t5-xxl

モデルサイズは fp16 で 45 GB くらいです.

8bit にして 3090 24 GB に収まります!

(8bit はバグがありましたが最新 transformers で修正されました https://github.com/huggingface/transformers/issues/20287)

## 日本語

一応 FLAN-T5 は日本語も学習しているようですが, そのままでは日本語は化けてしまいます.
Tokenizer あたり調整してあげないといけないっぽそうです(面倒だネ...)
github actions上でもしファイルが存在した場合はそのファイルを利用して処理する、という処理をruns-on: ubuntu/windows 環境でやる場合の備忘録

github actions上でもしファイルが存在した場合はそのファイルを利用して処理する、という処理をruns-on: ubuntu/windows 環境でやる場合の備忘録

具体的には以下の処理をする
- もし`requirements.txt`が存在したら、`pip install -r requirements.txt`を実行する

#### ubuntuの場合

```
if [ -f requirements.txt ]; then pip install -r requirements.txt; fi
```

#### windows powershellの場合

```
if( Test-Path .\requirements.txt ){ pip install -r requirements.txt }
```

以上

# 参考

https://win.just4fun.biz/?PowerShell/%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%83%BB%E3%83%95%E3%82%A9%E3%83%AB%E3%83%80%E3%81%AE%E5%AD%98%E5%9C%A8%E3%83%81%E3%82%A7%E3%83%83%E3%82%AF%E3%83%BBTest-Path

https://microsoftou.com/powershell-if/#toc2
JavaScript で Immer を使ってオブジェクトの階層が深いキーを immutable に消す（変更する）

- [Using produce | Immer](https://immerjs.github.io/immer/produce)

```js
import produce from 'immer'

const object = {
  a: {
    b: 1,
    target: 2,
  },
  c: 3,
  d: 4,
}
const newObject = produce(object, (draft) => {
  delete draft.a.target
})

console.log(object)
// => { a: { b: 1, target: 2 }, c: 3, d: 4 }

console.log(newObject)
// => { a: { b: 1 }, c: 3, d: 4 }
```
マイクラチュートリアル2-2 ピラミッド建築

``` lua
i = 3
j = i
s = 1
turtle.up()
turtle.select(s)

for n = 1, i do
  for n = 1, 4 do
    for n = 1, j * 2 do
      if turtle.getItemCount() == 0 then
        s = s + 1
        turtle.select(s)
      end
      turtle.placeDown()
      turtle.forward()
    end
    turtle.turnLeft()
  end
  j = j - 1
  turtle.turnRight()
  turtle.back()
  turtle.turnLeft()
  turtle.forward()
  turtle.up()
end
turtle.placeDown()
```
マスタリングTCP/IP入門 重要用語について自分の言葉で説明する Part1

# はじめに
ネットワーク知識習得のため、基本に立ち帰り[マスタリングTCP/IP―入門編―(第6版)](https://www.amazon.co.jp/%E3%83%9E%E3%82%B9%E3%82%BF%E3%83%AA%E3%83%B3%E3%82%B0TCP-IP%E2%80%95%E5%85%A5%E9%96%80%E7%B7%A8%E2%80%95-%E7%AC%AC6%E7%89%88-%E4%BA%95%E4%B8%8A-%E7%9B%B4%E4%B9%9F/dp/4274224473)を読むことにしました。
読んだ中で特に重要かなと思ったor興味を持った用語について、本書籍や他サイトの解説、自分の基礎知識と照らし合わせて超短く要約をしていきます。

# 1章 ネットワーク基礎知識

## OSI参照モデル
データ通信を7階層に分け、それぞれの機能、役割等を明確にしたモデル

| OSI参照モデル |
|:-:|
|アプリケーション層|
|プレゼンテーション層|
|セッション層|
|トランスポート層|
|ネットワーク層|
|データリンク層|
|物理層|

:::note info
このモデルは後々たくさん出てくるので、〜層は第何層か覚えておくと読みやすいです。
自分の覚え方↓
上から3層が`アプリをプレゼンしてセッション作成`、下から3層が`物理をリンクしてネットワーク作成`、`真ん中がトランスポート`みたいな。。。
:::

## IEEE
The Institute of Electrical and Electronics Engineers（米国電気電子技術者協会）
電気通信関係の規格の標準化をする団体。データリンク層の部分では、イーサネットの通信規格や無線の通信規格の標準を定めたりしている。
例えばIEEE802.3委員会によってイーサネットの仕様が改修され、その仕様のイーサネットのことを802.3Ethernetと呼ぶ。

## NIC
Network Interface Card 
ネットワークと通信するためのインターフェース。最近のパソコン（iPhoneやMac）では標準装備されているため特に追加でつける必要はないが、標準装備されていないものは別途購入して装備させる必要がある。1台の機器にNICが二つ付いてたりすることもある。

## 伝送速度
通信機器間でのデータの流れる速さのことを伝送速度という。単位はbps。これが大きくなると、1秒間に送ることのできるデータ量が増える。速度とはいっても物理的な電気信号の速さは一定なことに注意。`車線の多い道路=伝送速度`の速い回線というイメージ。帯域とも呼ばれる。

## スループット
実際にCPUでの演算時間などまで考慮して、ホストtoホストでデータの移動速度を計算したものがスループット。

## ロードバランサー
レイヤ4-7（トランスポート層からアプリケーション層まで）スイッチング機器のひとつ。複数のWebサーバーを設置し、その手前にロードバランサーを配置する。ロードバランサーに仮想URLを設定し利用者に公開する。利用者が仮想URLへアクセスすると、ロードバランサーは複数あるうちのどれか一つのサーバーにアクセスを割り振る。この仕組みによってWebサーバーへの負荷分散を行っている。

## ゲートウェイ
同じくレイヤ4-7の、データ中継機器。プロトコルの変換や中継を行っている。

## プロキシサーバー
ゲートウェイの一種。アプリケーションゲートウェイとも呼ばれる。
例えばAmazonで考えると、Amazonのサイトに私たちのパソコンからアクセスする際に、実際にAmazonのサーバーと私たちのパソコンで通信を行うのではなく、代理のサーバー（プロキシサーバー）が代わりに、私たちのパソコンが送信する要求に対して様々な応答を行ってくれる感じ。

# 3章 データリンク
## MACアドレス
基本的に1機器（NIC）に1つ固定で割り振られている48ビットの識別子。
ホストからホストへパケットを送受信する際には、IPアドレスとMACアドレスの2つが必要。


## イーサネット
データリンク層における代表的なプロトコル。
米国のXerox社と旧DEC社が考案した通信方式。その後1章のIEEEの説明でも書いた通り、IEEE802.3委員会によってイーサネットは規格化、標準化された。
昔は同軸ケーブルを使用して機器間を接続するのが一般的だったが、現在では端末とスイッチ間はツイストペアケーブル、スイッチ間を光ファイバーケーブルで繋ぐ構成が一般的となっている。

## 無線LAN
イーサネットは有線ケーブルを使用した通信の規格であったが、電波や赤外線、レーザー光線などを物理媒体とした無線通信にも通信規格は様々存在する。無線通信の中でオフィス内のようなLocalAreaNetworkの範囲を高速で接続するものを特に無線LANと呼ぶ。
例としてイーサネットと同様にIEEEが標準化している規格にIEEE802.11aやIEEE802.11acがあり、これらは5GHz帯を使用することを規定している。

## FTTH
フレッツ光などでお馴染みの光回線通信方式の一つ。通信会社のネットワークと繋がった光回線を家庭やオフィス近くまで引き込んで、ONU（Optical Network Unit）からルーターに繋ぎ、ルーターから各機器に接続する。

# まとめ
1章〜3章までの内容をまとめました。
次回4章（IP: Internet Protocol）からの内容も書いていく予定です。