OmniAICreator/Qiita-1.07M huggingface dataset:
Expressで一体何が行われているのか？

expressを使い始めて一体バックエンドで行われているのか不思議に思ったので調べてみました。
そもそも、httpリクエストやhttpレスポンスが何なのかを理解しなくてもアプリを作成出来ればよいはずなんだけど、理解しないと複雑なルーティングやリクエストやレスポンスを引き継いだり受け渡したりしないと作り上げられないという現実にぶち当たる・・・ので避けては通れないし、避け続けているとスキルアップしない、モチベーションの低下、退場となりかねないので、素人なりに分かるところまでやってみます！

まずはexpressのデフォルトを立ち上げて`app.js`にあるこの部分。

```app.js
var express = require('express'); //2行目
var app = express(); //10行目
```
ここでまず混乱したのは`routes/index.js:1:2`にある

```
var express = require('express');
var router = express.Router();
```
との整合性。検索してサイトの例でよく見る

```
app.get("/", (req, res) => {
    res.status(200).send("OK");
});
```
のような記載。変数appにgetやpost, put, deleteを付けるんならワザワザ`router = express.Router();`としなくてもイイんじゃね？と・・・もっと言うとappとrouterで何が違うの？ってなった。
すぐに、`app.get()`は`router.get()`の簡略化してサンプルを作成していると理解出来ます。`app.js`はアプリケーションを起動するためにあって個別の細々した機能はそれぞれ別ファイルに書くべき、そのためにexpressのメソッドとしてRouterが独立している。
では、ドキュメントでそのあたり確認してみましょう！
[Express APIリファレンス]("https://expressjs.com/ja/4x/api.html#router")のナビゲーションウィンドウのRouterの説明文に
>You can think of it as a “mini-application,” capable only of performing middleware and routing functions.

関数であること、よりわかりやすく'ミニアプリケーション'と記載されてます。（記載はしませんがapp側にはtop-levelとなっています）
これで、変数appで利用されるroutingと変数routerのそれがほぼ同じ役割、使い分けするためだけに分けているということが分かります。
もっと言うと、変数appがアプリケーション本体、変数routerはミニアプリケーションという階層構造になっていることも分かります。
では、[expressのソースコード]("https://github.com/expressjs/express/blob/master/lib/application.js")でも確認しましよう！

```
//application.js
var Router = require('./router'); //17行目
var methods = require('methods');　//methodsってなんだ？
var middleware = require('./middleware/init');
```
router.jsをrequireしていますね。反対にrouter.jsには反対のrequireはないので階層構造になっています。

さて、もう少し突っ込んでみます。では、`app.get()`や`router.post()`の第２引数のコールバック関数で何で`req, res, next`を指定してるの？っていう疑問に進みます。いや、そんなの分かるに決まってるやん！とか、そのまま型として覚えておけばイイんだよ、とか、言われそうですが、疑問に思ったもんは仕方ありません。

```
router.get('/', function (req, res) {  //app.getでも構わない
  res.send('hello world')
})
```
これですね。第１引数がエンドポイント、第２引数がコールバック（コールバックについてはまた詳しくやりたいですが、今のところは関数内の関数くらいに思っておいてください）で、何を指定出来るのか、まずはリファレンスを見てみます。


>.middleware function.
>.series of middleware functions (separated by commas).
>.An array of middleware functions.
>.combination of all of the above.

となってます。取り敢えず、ミドルウェア関数ならカンマで繋げればどんなけでもつなげることが出来ると分かります。でも知りたいのは`function(req, res)`の部分。
色々調べて結果、ここに行き着きました。

```
//lib/routers/layer.js
function Layer(path, options, fn) {
  if (!(this instanceof Layer)) {
    return new Layer(path, options, fn);
  }

  debug('new %o', path)
  var opts = options || {};

  this.handle = fn;
  this.name = fn.name || '<anonymous>';
  this.params = undefined;
  this.path = undefined;
  this.regexp = pathRegexp(path, this.keys = [], opts);

  // set fast path flags
  this.regexp.fast_star = path === '*'
  this.regexp.fast_slash = path === '/' && opts.end === false
}
```
おじさん、このあたりが`function(req, res)を書いているように思うんだ・・・・

未完
【備忘】一括コマンド

#備忘として
ブランチコミット後にメインブランチにマージとリモートリポジトリに送るのがたまにめんどくさくなる。そういう時に以下のコマンドで一括登録できるから、ただ単純に備忘としてここに記載する。



     git push origin HEAD && git checkout main && git merge - && git push origin HEAD


#仮に以下のようなエラーが出た場合

>! [rejected]        HEAD -> main (fetch first)
error: failed to push some refs to 'https://github.com/username/repos.git'
hint: Updates were rejected because the remote contains work that you do
hint: not have locally. This is usually caused by another repository pushing
hint: to the same ref. You may want to first integrate the remote changes
hint: (e.g., 'git pull ...') before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.

とりあえず強制pushで解決

     git push -f origin main


#参考

![GitHubにpushする時にerror: failed to push some refs と表示されてpushできない時](https://qiita.com/kazuki0714/items/ceda3a6721a9a99082de)
【Swift】UIAlertControllerを簡略化してみよう

#はじめに
UIAlertControllerを使うときにアクションなどが多いと同じ処理を何回も複数のファイルに書いたりするのって少し面倒ですよね。
そんな時に簡略化できないかを考えてみます。

#やりたいこと

```Swift
let alert = UIAlertController(title: "タイトル", message: "メッセージ", preferredStyle: .alert)
        let action1 = UIAlertAction(title: "ボタン1", style: .default, handler: { (_) in
            print("button1")
        })
        let action2 = UIAlertAction(title: "ボタン2", style: .default, handler: { (_) in
            print("button2")
        })
        let action3 = UIAlertAction(title: "ボタン3", style: .default, handler: { (_) in
            print("button3")
        })
        alert.addAction(action1)
        alert.addAction(action2)
        alert.addAction(action3)
present(alert, animated: true, completion: nil)
```
これを、省略していきましょう。

#実装
メソッドチェーンを使うので、[前回](https://qiita.com/REON/items/780f341b5b80ae4c9e6b)と同じようなことをします。
ポイントは`return self`です。

```swift 
extension UIViewController {
    func Alert(title: String, message: String) -> UIAlertController {
        let alert = UIAlertController(title: title, message: message, preferredStyle: .alert)
        return alert
    }
}

extension UIAlertController {
    func addAction(title: String, action: @escaping () -> Void) -> Self {
        addAction(UIAlertAction(title: title, style: .default, handler: { _ in action() }))
        return self
    }
}
```

このように書くと、

```swift 
let alert = Alert(title: "タイトル", message: "メッセージ")
    .addAction(title: "ボタン１", action: { print("button1") })
    .addAction(title: "ボタン２", action: { print("button2") })
    .addAction(title: "ボタン３", action: { print("button3") })
present(alert, animated: true)
```
このようにシンプルに書くことができます。

#おわりに
チーム開発などでは独自の書き方はあまりお勧めできませんが、、、
【Swift】メソッドチェーンで見やすく

#はじめに
コードでUIを作成するときに、メソッドチェーンを使いえば見やすくなるので、それを紹介します。
本当はジェネリクスなども使ったほうがいいのですが、今回は使いません。

#メソッドチェーンとは？
その名の通り、メソッドを鎖（チェーン）のように書いていくということです。
例えば、普通は以下のように書くと思います。

```swift
let label = UILabel()
label.frame.origin = CGPoint(x: 100, y: 100)
label.frame.size = CGSize(width: 100, height: 40)
label.text = "text"
label.layer.cornerRadius = 25
label.backgroundColor = .red
label.textColor = .white
label.textAlignment = .center
self.view.addSubview(label)
```
これでもいいのですが、これだと`label`を複数書いるのでもう少し見やすく書けないか考えてみます。
メソッドチェーンをつかえば以下のように書くことができます。

```swift
let label = UILabel()
    .origin(x: 100, y: 100)
    .size(width: 100, height: 40)
    .backgroundColor(.red)
    .cornerRadius(25)
    .text("テキスト")
    .textColor(.white)
    .textAlignment(.center)
self.view.addSubview(label)
```
こちらの方が、すっきりしていていいですよね。

#実装
メソッドチェーンのポイントは`return self` です。
例えば、`.origin(x: 100, y: 100)`を例にとってみましょう。
UILabelはUIViewを継承しているので、UIViewをextensionしてみましょう。

```swift
extension UIView {
    func origin(x: CGFloat, y: CGFloat) -> Self {
        self.frame.origin = CGPoint(x: x, y: y)
        return self
    }
}
```

`self.frame.origin`のselfはこのoriginメソッドを使うものを表しています。今で言うと定数labelですね。
戻り値に大文字の`Self`を使うことで、戻り値をUIViewにし、メソッドを鎖のように連ねていくことができるというわけです。
これを今回を例に全て書いてあげると、

```swift
extension UIView {
    func origin(x: CGFloat, y: CGFloat) -> Self {
        self.frame.origin = CGPoint(x: x, y: y)
        return self
    }
    func size(width: CGFloat, height: CGFloat) -> Self {
        self.frame.size = CGSize(width: width, height: height)
        return self
    }
    func backgroundColor(_ color: UIColor) -> Self {
        self.backgroundColor = color
        return self
    }
    func cornerRadius(_ radius: CGFloat) -> Self {
        self.layer.cornerRadius = radius
        return self
    }
}

extension UILabel {
    func text(_ text: String) -> Self {
        self.text = text
        return self
    }
    func textColor(_ color: UIColor) -> Self {
        self.textColor = textColor
        return self
    }
    func textAlignment(_ alignment: NSTextAlignment) -> Self {
        self.textAlignment = alignment
        return self
    }
}
```

このようにしてあげることで、メソッドチェーンが使用可能になります。

#番外編
番外編として、クロージャでもかけるので、それを紹介しておきます。

```swift 
extension UILabel {
    func chain(_ closure: (Self) -> Void) -> Self {
        closure(self)
        return self
    }
}
let closureLabel = UILabel()
    .chain { label in
        label.frame.origin = CGPoint(x: 100, y: 100)
        label.frame.size = CGSize(width: 100, height: 40)
        label.backgroundColor = .red
        label.layer.cornerRadius = 25
        label.text = "text"
        label.textColor = .white
        label.textAlignment = .center
    }
self.view.addSubview(closureLabel)
```

こちらはわざわざ一つ一つメソッドを定義しなくても容易ので、楽ですね。

#おわりに
おわりです。
LIMITLESS

LIMITLESS 超加速学習を読みました。
概ねAgree。

私の意見を以下に示します。

#「人に教えること」は超加速学習にならない
と思う。
「人に教えること」というのは、
>（A）自分の頭の中を整理して、何を教えるかを明確にする。
>（B）相手に理解してもらう。

ということになる。（A）は有益で大切だ。しかし、（B）は相手のレスポンスを受けて、相手が理解したかどうかを確認する必要がある。教える相手にもよるが、（B）は効率的に進めることができないと思う。

#「記憶」と「忘れること」のバランスが重要
あとは、「記憶」と「忘れること」のバランスが重要だと思う。
「記憶」を強化すると、頭がパンクする。
なので、「忘れること」も重要。
Google先生に聞けば良いことを覚える必要はない。
会話している相手の名前は、絶対に覚えないと失礼になる。

#＜今後の予定＞

・「リミットレス」という映画があるので、それを見ること。
・「リミットレス」という他の本があるので、それを読むこと。
開発手法についての知識

#本記事について
プログラミング初心者が開発手法に関する知識を学んだので、その備忘録として載せております。

どうかお手柔らかにお願いいたしますm (- -)(_ _)ペコリ

##アジャイル型開発（石橋叩くタイプ）
一度にまとめてでは無く、少しずつ確認を挟みながら開発を進めていくことが特徴。
利用者の反応や関係者からの継続的なレビューを得ながら計画を調整しつつ進める。
→石橋を叩いて渡るタイプの開発
スクラムを用いることがある。
リリースの頻度が高い。

##ウォーターフォール型開発（尻カッチンタイプ）
初めに決めた要件を、ある期限までに完了することが特徴。
契約→開発→納品というフロー。
厳密な要件定義と納期に合わせて進捗確認を行うことが理想。
上流を固めていれば下流も固くなる。上流がしっかりしていないと下流に行けば行くほどリカバリーが難しくコストも時間も労力もかかる。

##スクラム
開発を進めるチームの単位。
チーム全員が主体性を持ってプロダクト完成に向けた責任を持つことが特徴

機能を細かくリリースするまでの期間を「スプリント」として各スプリント毎にレビューを行う

管理を自動化することでミスをなくし、労力を減らす効率化を図る

##Sider
GitHubに対応したコードレビュー自動化サービス

コードレビュー（他者にマージする前に確認をとってもらう）を自動で行ってくれる
設定したルールに反していないか自動で判断（例　インデントなど）

SiderはGitHubと公式に連携をしているため、GitHub上で駆動する。
GitHub上にPushした、プルリクエスト上のコードに対してチェックを行う。

Ruby、PHP、JavaScript、CSS、Java、Python、Go、Swiftなどに対応している。

##CircleCI
CI/CDを自動で実行するクラウドサービス
追加・変更されたアプリケーションのテストやテストが完了して問題がなかったコードのデプロイ、自動で実行するサービス

Facebook、メルカリなどが導入

##CI/CD（概念　Continuous Integration/Continuous Delivery）
CI　継続的インテグレーション。開発したコードのテストを定期的に自動化する。
CD 継続的デリバリー。書いたコードを自動で本番環境にデプロイできる状態に整える。

変更したコードは自動でチェック、問題がなければ自動でデプロイ
定期的にテストは自動で実行させ確認、自動でデプロイできる状態に整える。

ソフトウェアの変更を常にテストして自動で本番環境にリリース可能な状態にしておくソフトウェア開発の手法

人的負担が少ない。
リリース頻度の高いアジャイル型開発において有効。

以上です。
Rails mimemagicエラー

mimemagicエラーが発生。詳しくは以下から。

https://qiita.com/Esfahan/items/45c0cdeb29509b7ec1c5#rails-525-6036-6131%E3%81%AFmimemagic%E3%81%AB%E4%BE%9D%E5%AD%98%E3%81%97%E3%81%AA%E3%81%8F%E3%81%AA%E3%81%A3%E3%81%9F327%E8%BF%BD%E8%A8%98

docker-compose buildをしたら、以下のエラーが発生。
私がしているのは、dockerとrailsでアプリを作っている最中。

##今回のエラー

```
#13 0.732 Fetching https://github.com/manfe/refile.git
#13 2.642 Fetching gem metadata from https://rubygems.org/............
#13 4.718 Resolving dependencies...
#13 5.021 Your bundle is locked to mimemagic (0.3.5), but that version could not be found
#13 5.021 in any of the sources listed in your Gemfile. If you haven't changed sources,
#13 5.021 that means the author of mimemagic (0.3.5) has removed it. You'll need to update
#13 5.021 your bundle to a version other than mimemagic (0.3.5) that hasn't been removed
#13 5.021 in order to install.
```

##解決
解決方法は記事に、「Rails 5.2.5, 6.0.3.6 and 6.1.3.1がリリースされているから、これらはmimemagicに依存しなくなったのでアップグレードすればOK」
とあったので、以下の手順でアップグレード。

Gemfileのバージョンを6.1.3.1に書き換える。

```
gem 'rails', '6.1.3.1'
```

次に、bundle updateコマンドを実行する。ここでは、Railsのgemだけをアップデートする。

```
$ bundle update rails
```


よかった。。エラー解決に3時間かかった。。。。。。
これも経験かな、、、

今回は以上です。ありがとうございました。
7セグで、任意の値を表示させてみた

タイトルの通り、好きな数字を入力したら、7セグに出力されるものを作ります。

#使用したもの
- Raspberry Pi 4 Model B
- ブレッドボード
- ジャンパ線
- 赤色7セグ([A-551SRD](https://akizukidenshi.com/catalog/g/gI-00639/))

#1. 配線する

下の画像のように、ジャンパ線を使いつなげていきます。
![7seg.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/549741/b9723c6c-266a-172a-daa2-20ab4cc193e4.gif)
７セグの足とGPIOのポート間は以下の通りです。

- 十の位

| 7セグの足 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 |
|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|
| GPIO | 22 | 18 | 電源線 | 16 | 省略 | 7 | 11 | 電源線 | 13 | 15 |

- 一の位

| 7セグの足 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 |
|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|
| GPIO | 32 | 36 | 電源線 | 38 | 省略 | 37 | 35 | 電源線 | 33 | 31 |


#2. プログラム

SSHの場合は、_sudo nano_ でファイルを作成します。
言語はpythonを使いました。

```python:7seg_anyvalue.py

import RPi.GPIO as GPIO
from time import sleep

i = int(input('表示する値を入力してください：'))

GPIO.setmode(GPIO.BOARD)
ports1 = [
    11, 7,16,18,22,13,15,12]
ports2 = [
    35,37,38,36,32,33,31,40]
GPIO.setup(ports1, GPIO.OUT)
GPIO.setup(ports2, GPIO.OUT)

numbers = [
    [1,1,1,1,1,1,0,0], #0
    [0,1,1,0,0,0,0,0],
    [1,1,0,1,1,0,1,0],
    [1,1,1,1,0,0,1,0],
    [0,1,1,0,0,1,1,0],
    [1,0,1,1,0,1,1,0],
    [1,0,1,1,1,1,1,0],
    [1,1,1,0,0,1,0,0],
    [1,1,1,1,1,1,1,0],
    [1,1,1,0,0,1,1,0],
    [0,0,0,0,0,0,0,0], #10
    ]


def show_num(no):
    l = int(no / 10)
    r = int(no % 10)
    ns = numbers[r]
    for i, n in enumerate(ns):
        n = 1 if n == 0 else 0
        GPIO.output(ports2[i], n)
    ns = numbers[l]
    for i, n in enumerate(ns):
        n = 1 if n == 0 else 0
        GPIO.output(ports1[i], n)
try:
    while True:
        show_num(i)
        sleep(10)
        print('表示なう')


except KeyboardInterrupt:
       pass

GPIO.cleanup()

```

実行すると、表示させたい値を聞かれるので入力、7セグに反映されます。
その後は、10秒毎に「表示なう」がPC側に出ます。
終了したい場合は、「control」＋「C」で終わります。

#応用

7セグの数を増やして、計算機が作れそうだと思いました。
また、タクトスイッチを押すと、ランダムに値が出るなども、おもしろそうです。
7セグの世界も深いですね。

#参考図書

クジラ飛行机 著
[「やさしくはじめるラズベリー・パイ 電子工作でガジェット＆簡易ロボットを作ってみよう」](https://www.amazon.co.jp/gp/product/B0721WG731/ref=dbs_a_def_rwt_hsch_vapi_tkin_p1_i1)
ーマイナビ出版

※ 本記事では上記の図書を参考に、改良して使わさせていただきました。
[Ubuntu18] error occured processing lib64go7-x32-cross(NewVersion2) への対処

# 概要

こんなエラーが発生した。
タイミングとしては、ubuntuにログインした瞬間と、`apt update`した後に発生。

```bash
error occured processing lib64go7-x32-cross(NewVersion2) The package list or status file could not be parsed or opened
```

つまり、`apt update`できない状態に陥った。

この時、一発で解決できたが、解決策が英語でしか書かれていない（しかも見つけにくかった！）ので記事を共有しておこうと思いました。

# その他のエラー

解決策が書かれていた記事には、以下のようなエラーで困っている人がいた。

```bash
$ apt-get update
E: Problem parsing dependency Depends
E: Error occurred while processing vbuf (NewVersion2)
E: Problem with MergeList /var/lib/apt/lists/ftp.debian.org_debian_dists_squeeze_main_binary-amd64_Packages
E: The package lists or status file could not be parsed or opened.
E: _cache->open() failed, please report.
```

# 対処

これだけで治った。

```bash
$ dpkg --clear-avail
```

次のコマンドも掲載されているが、まだ何もinstallしていない、ubuntuを構築した直後だったので、実行する必要はなかった。

```bash
$ rm /var/lib/apt/lists/* --force
```

# 情報元

[LinuxQuestions.org - apt-get problem (Problem parsing dependency Depends)](https://www.linuxquestions.org/questions/debian-26/apt-get-problem-problem-parsing-dependency-depends-906264/)
DjangoでForeign Keyを逆に辿りたい

DjangoでForeign Keyを逆にたどるために色々調べたのでメモ。
間違っているとことかあれば教えてほしい。


例えば、病院に勤務する医者のモデルを考える。

```python
class Hospital(models.Model):
    name = models.CharField(max_length=20)

    def __str__(self):
        return self.name


class Users(models.Model):
    name = models.CharField(max_length=10)
    hospital = models.ForeignKey(
        Hospital, on_delete=PROTECT, null=True, blank=True, )

    def __str__(self):
        return self.name
```

ユーザに対し、１つの病院を紐付けている。
医師モデルの中に、所属している病院を登録しているイメージだ。


ではここから、<b>ある病院に所属している医師のリスト</b> を取得したい

その前に一度 <b>views.py</b>を見てみよう。以下のように書いた。

```python
from django.views import generic
from .models import Users, Hospital
from django.shortcuts import get_object_or_404


class HospitalView(generic.ListView):
    model = Hospital


class DetailView(generic.DetailView):
    model = Hospital
    template_name = 'testapp/detail.html'

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)  # はじめに継承元のメソッドを呼び出す
        hospital = Hospital.objects.get(name=context["hospital"])
        context["users"] = hospital.users_set.all()
        return context

```

以下の様にすれば、データを受け渡したテンプレート内で <b>users</b> としてその病院に所属している医師のリストを取得することができた。

ポイントは、

```python
hospital = Hospital.objects.get(name=context["hospital"])
#と
hospital.users_set.all()
#の部分だ。

hogehoge = 親.objects.get(name = 子の名前)

hogehoge.子モデル名_set.all()

```

という具合になった。

ちなみにテンプレートは以下のようにすれば良い。

```html
{{hospital}}

<ul>
    {{% for user in users %}
    <li>{{ user }}</li>
    {% endfor %}}
</ul>
```
PuppeteerのElementHandleを拡張してclosestを定義した

PuppeteerのElementHandleに対してjQueryのclosestのようなこと（祖先要素のうち、指定したセレクタにマッチする一番近いのを取得する）をしたかったのだけど、そんなメソッドは用意されていないようだったので、拡張することにした。

が、TypeScriptで書いているので、型定義もどうにかしないといけないということで、試行錯誤してどうにか目的を達成したようなので、その成果だけシェアしておこうと思う。

```typescript
import { ElementHandle } from 'puppeteer/lib/cjs/puppeteer/common/JSHandle';

declare module 'puppeteer' {
  interface ElementHandle<ElementType extends Element = Element> extends JSHandle {
    closest(sel: string): Promise<ElementHandle | null>
  }
}

declare module 'puppeteer/lib/cjs/puppeteer/common/JSHandle' {
  interface ElementHandle extends JSHandle {
    closest(sel: string): Promise<ElementHandle | null>
  }
}

ElementHandle.prototype.closest = async function(sel: string): Promise<ElementHandle | null> {
  const find = async function(e: ElementHandle, sel: string): Promise<ElementHandle | null> {
    const parent = await e.$x('..').then(elems => elems.length > 0 ? elems[0] : null)
    if (parent == null) {
      return null
    } else if (await parent.evaluate((node, sel) => node.matches(sel), sel)) {
      return parent
    } else {
      return find(parent, sel)
    }
  }
  return find(this, sel)
}
```

メソッドの型情報を2ヶ所に書かないといけないのはどうにかならないものだろうか。
staticをインスタンス化した後から指定するとどうなるか


#はじめに
最近、```static```がインスタンス化したものにも影響を及ぼすということを知らずに使ってしまい、その挙動に戸惑ったことがあるのでそのことについて書きたいと思います。
この記事を読めば```static```の理解が少し深まります。



まず、以下のような課題があったとします。

Q. 以下の仕様を満たし、次の出力結果が出るようにコードを追記せよ。※環境は```PHP7.4```とします。
 
出力結果

```
田中さんは日本人です。
ジュリーさんはアメリカ人です。
黄さんは中国人です。
ミュラーさんはドイツ人です。
```

```php
<?php

class Person
{
    /* コードを記述 */
}

$person1 = new Person("田中", "日本");
$person2 = new Person("ジュリー","アメリカ");
$person3 = new Person("黄","中国");
$person4 = new Person("ミュラー","ドイツ");

$persons = [ $person1, $person2, $person3, $person4 ];
foreach ($persons as $person) {
    echo /* コードを記述 */ . "さんは" . /* コードを記述 */ . "人です。\n";
}
```



さて皆さんは無事に書けましたかね
コード例は以下になります。

```php
<?php

class Person
{
    public $name;
    public $country;

    public function __construct($name,$country) {
        $this->name = $name;
        $this->country = $country;
    }
}

$person1 = new Person("田中", "日本");
$person2 = new Person("ジュリー","アメリカ");
$person3 = new Person("黄","中国");
$person4 = new Person("ミュラー","ドイツ");

$persons = [ $person1, $person2, $person3, $person4 ];
foreach ($persons as $person) {
    echo $person->name . "さんは" . $person->country . "人です。\n";
}
```

```
田中さんは日本人です。
ジュリーさんはアメリカ人です。
黄さんは中国人です。
ミュラーさんはドイツ人です。
```

本来はこれで問題ないのですが、当初私は、スコープ演算子を使って、どこからでもアクセスができる```static```を使うのもいいんじゃない？いけるんじゃね？と考えた結果、以下のようにコードを考えました。

````php
<?php

class Person
{
    public static $name;
    public static $country;

    public function __construct($name,$country) {
        self::$name = $name;
        self::$country = $country;
    }
}

$person1 = new Person("田中", "日本");
$person2 = new Person("ジュリー","アメリカ");
$person3 = new Person("黄","中国");
$person4 = new Person("ミュラー","ドイツ");

$persons = [ $person1, $person2, $person3, $person4 ];
foreach ($persons as $person) {
    echo Person::$name . "さんは" . Person::$country . "人です。\n";
}
```

すると
出力結果は

```
ミュラーさんはドイツ人です。
ミュラーさんはドイツ人です。
ミュラーさんはドイツ人です。
ミュラーさんはドイツ人です。
```
となり、あれ？ミュラーさんが4人も出てきたぞ！なんでやねんおかしいやろ！？
ってことで知人エンジニアに質問をしたり調べたりでこうなる理由が解明できました。

要はstatic変数はクラスレベルの変数のため、static変数を変更すると、そのクラスのすべてのインスタンスに影響するとのことです。

以下の記事の```なぜstaticを乱用してはいけないのか```が特に参考になりました。
https://qiita.com/ue_knnk/items/fa84b8bc30ba319e5744

なので今回のコードに関しては、コンストラクタで、```$name```、```$country```を代入してそれらがstatic変数になるという仕組みになってしまった結果、
一番最後に代入された```ミュラー```、```ドイツ```がstatic変数となってしまい既にインスタンス化された他の3つにも影響し、このような出力結果になってしまったという訳です。(なるほど)

#最後に
今回は```static```についての記載をしましたが、私を含めこれを知らなかった初学者もいると思いますので(いなかったらすみません)少しでも役立って貰えれば幸いです。
【Rails】destroyで関連するレコードも一緒に削除する方法

たとえば、自分の投稿したメッセージを削除する機能を実装しようとした際に、そのメッセージにいいねがついていると、いいねも一緒に削除しないといいねだけが残ってしまい、不具合の原因となってしまいます。




# 方法
Modelに```dependent: :destroy```を追記してあげれば、railsがよしなに削除してくれます。

```ruby
# message.rb
has_many :likes, dependent: :destroy
```

ちなみに、viewはこのように記述しております。

```erb
<%= link_to "削除",{controller: "messages", action: "destroy", message_id: message.id, user_id: current_user.id, score_id: @score.id }, method: :delete, remote: true, data: {confirm: "削除しますか？"} %>
```
【Mac版】シェルスクリプトを作ってダブルクリックのみでビルトインウェブサーバを起動させる方法

## ビルトインウェブサーバについて
[プライベートIPアドレスの用途](https://qiita.com/rimorimo/items/9ee259ffb492a073884a#%E3%83%97%E3%83%A9%E3%82%A4%E3%83%99%E3%83%BC%E3%83%88ip%E3%82%A2%E3%83%89%E3%83%AC%E3%82%B9%E3%81%AE%E7%94%A8%E9%80%94)参照．

## プライベートIPアドレスの取得について

[ターミナル上でプライベートIPアドレスを調べる方法 1](https://qiita.com/rimorimo/items/9ee259ffb492a073884a#%E3%82%BF%E3%83%BC%E3%83%9F%E3%83%8A%E3%83%AB%E4%B8%8A%E3%81%A7%E3%83%97%E3%83%A9%E3%82%A4%E3%83%99%E3%83%BC%E3%83%88ip%E3%82%A2%E3%83%89%E3%83%AC%E3%82%B9%E3%82%92%E8%AA%BF%E3%81%B9%E3%82%8B%E6%96%B9%E6%B3%95-1)参照．

## シェルスクリプトの作成
デスクトップ上にシェルスクリプトを作成

```
touch ~/Desktop/builtin_webserver.command
```

`builtin_webserver.command`に下記コードを記述

例）プライベートIPアドレスが`192.168.100.158`の場合

```builtin_webserver.command
#!/bin/sh

# ドキュメントルートへ移動
cd /Library/WebServer/Documents

# ビルトインウェブサーバを起動
php -S 192.168.100.158:8000
killall Terminal
```

下記コマンドを実行して`.command`ファイルに実行権限を与える．

```
chmod u+x ~/Desktop/builtin_webserver.command
```

終了コマンドは`Ctrl-C`

これで`builtin_webserver.command`をダブルクリックするだけで，ビルトインウェブサーバが起動しローカルサーバを立てることができるようになった．

ネットワーク環境が変わるとプライベートIPアドレスも変わってしまうので，都度`builtin_webserver.command`を書き換える必要がある．
VSCode の JS / TS のメソッド補完で括弧を入力する設定

## VSCode の JS / TS のメソッド補完で括弧を入力する設定

```json
{
    "javascript.suggest.completeFunctionCalls": true,
    "typescript.suggest.completeFunctionCalls": true
}
```

## false のとき

![2021-03-28 04.56.54.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/177661/a8165417-c701-99ae-1cce-7a3901981f8c.gif)

## true のとき

![2021-03-28 04.55.42.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/177661/afb13cee-3468-58f4-e03d-c12030998713.gif)
【Mac版】ターミナル上でプライベートIPアドレスを調べる方法

## ターミナル上でプライベートIPアドレスを調べる方法 1

下記コマンドを入力する.

```
ifconfig
```

下記出力が得られる.

```
...
en0: flags=XXXX<UP,BROADCAST,SMART,RUNNING,SIMPLEX,MULTICAST> mtu XXXX
	options=XXXX<RXCSUM,TXCSUM,TSO4,TSO6,CHANNEL_IO,PARTIAL_CSUM,ZEROINVERT_CSUM>
	ether XX:XX:XX:XX:XX:XX 
	inet6 XXXX::XXXX:XXXX:XXXX:XXXX%en0 prefixlen 64 secured scopeid 0xb 
	inet 192.168.100.158 netmask 0xffffff00 broadcast 192.168.100.255
	inet6 XXXX:XXXX:XXXX:XXXX:XXXX:XXXX:XXX:XXXX prefixlen 64 autoconf secured 
	inet6 XXXX:XXXX:XXX:XXXX:XXXX:XXXX:XXXX:XXXX prefixlen 64 autoconf temporary 
	inet6 XXXX:XXXX:XXX:XXXX:XXX:XXXX:XXXX:X prefixlen 64 dynamic 
	nat64 prefix 64:XXXX:: prefixlen 96
	nd6 options=201<PERFORMNUD,DAD>
	media: autoselect
	status: active
...
```

上記コマンドだと余計な情報が多過ぎる．

プライベートIPアドレスはデバイス名`en0`の`inet`にある（今回の場合は`192.168.100.158`）

古い年式のMacの場合はプライベートIPアドレスが割り当てられているデバイス名は`en1`となっている場合が多い.

せっかくなので，プライベートIPアドレスの部分のみ取得を試みる．

```
ifconfig en0 inet
```

下記出力が得られる.

```
en0: flags=XXXX<UP,BROADCAST,SMART,RUNNING,SIMPLEX,MULTICAST> mtu XXXX
	options=XXXX<RXCSUM,TXCSUM,TSO4,TSO6,CHANNEL_IO,PARTIAL_CSUM,ZEROINVERT_CSUM>
	inet 192.168.100.158 netmask 0xffffff00 broadcast 192.168.100.255
	nat64 prefix 64:ff9b:: prefixlen 96
```

**あと少し！**

`awk`コマンドを用いて，スペース区切り2つ目の文字列を取得

```
ifconfig en0 inet | awk '{print $2}'
```

下記出力が得られる.

```
flags=XXXX<UP,BROADCAST,SMART,RUNNING,SIMPLEX,MULTICAST>
192.168.100.158
```

1行目が余分なので力技で**正規表現**で絞り込み

```
ifconfig en1 inet | awk '{print $2}' | grep '^192'
```

下記出力が得られる.

```
192.168.100.158
```

**プライベートIPアドレスの取得に成功！**

## ターミナル上でプライベートIPアドレスを調べる方法 2

`ifconfig`と比べると情報量が少ないが実はもうひとつ，ネットワーク状況を調べるための有名なコマンドが存在する．それが`networksetup -getinfo Wi-Fi`である．

```
networksetup -getinfo Wi-Fi
```

下記出力が得られる.

```
DHCP Configuration
IP address: 192.168.100.158
Subnet mask: 255.255.255.0
Router: 192.168.100.1
Client ID: 
IPv6: Automatic
IPv6 IP address: none
IPv6 Router: none
Wi-Fi ID: XX:XX:XX:XX:XX:XX
```

先程と同様に**正規表現**と`awk`コマンドを用いて取得を試みる．

```
networksetup -getinfo Wi-Fi | grep '^IP address' | awk '{print $3}'
```

下記出力が得られる.

```
192.168.100.158
```

**プライベートIPアドレスの取得に成功！**

## プライベートIPアドレスの用途
**PHP**でWebサービスを開発する際に**ビルトインウェブサーバ**を使い，ローカルサーバを立て他のマシンから接続し動作検証を行う際，プライベートIPアドレスを把握しなければならないケースが出てくる．

## ビルトインウェブサーバの使い方
**ドキュメントルート**へ移動する．

```
cd /Library/WebServer/Documents
```

下記コマンドでも可（フルパス表記）

```
cd ~/../../Library/WebServer/Documents
```

**ビルトインウェブサーバ**を使いローカルサーバを立てる

例）プライベートIPアドレスが`192.168.100.158`の場合

```
php -S 192.168.100.158:8000
```
DBとサーバーって結局何者？


##前提
・私自身、初学者ですので盲信なさらずに。
・できるだけ噛み砕いて抽象化して記載しています。

##目的
・コードは好きだが、「インフラ側があやふやだ...」ってなったので、備忘録作成。
・初学者の役に立てたら。という思いから。

###DB （データベース）
#####〜情報の倉庫〜
データベースは「情報の倉庫」です。
ユーザーから入力された情報・予め入れておく情報などが入っています。

通販を例に挙げると
商品の情報 (DB) ＞ 出力 ＞ 画面に表示
お客様情報 ＞ 入力 ＞ 保存 (DB)

（有名DB）
MySQL , PostgreSQL , Oracle Database , SQLite , MongoDB


### サーバー
#####〜情報の配達員〜
サーバーは「情報の配達員」です。
サーバー内の情報をクライアント（ユーザー）に運びます。
（＊厳密には違うが、あくまでイメージ）

通販を例に挙げると
ユーザー（ページ情報要求） ＞ サーバー（探して提供） ＞ 画面に表示

##### さらに深堀り
サーバーは「Webサーバー」,「APサーバー」,「DBサーバー」に大きく分けることができます。

「Webサーバー」
クライアントの要求したページ情報を提供（HTMLなど）

「APサーバー」
プログラムを提供。
Webサーバーから送られてきたリクエストを元に、PHPなどの動的ファイルの実行を行います。
必要であれば、DBから情報をとってきます。

「DBサーバー」
DBの情報を提供（ユーザー情報など）

##### 結局DBとサーバーの関係とは...
私はずっと勘違いしていたのですが、サーバーという大枠の中にDBが存在します。
・サーバーと言う大枠（配達屋）がある
・更に3つに小分けできる
・そのうちのDBサーバーを用いて、DBから情報をとってくる。
という表現がしっくりくると思います。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/783286/e8734b87-6a65-5261-b7f8-fb0cd4c00bd4.png)

## まとめ
・DB（データベース）は情報の倉庫
・サーバーは情報の配達員
・サーバーは Web , AP , DBサーバーに分けられる
・そのうちのDBサーバーを使ってDBにアクセスしている。


## 所感
初のアウトプットを行うにあたって、「間違った情報を流してはいけない」という思いから、とにかく調べました。
調べる過程で、自分は抽象的な表現の記事の方が理解しやすい。という気づきがありました。
また、アウトプットを行う際、抽象表現の言語化を行うため、知識の定着にもなったと感じました。

## ソース
#####全体
[https://www.itscom.co.jp/forbiz/column/office-environment/1087](https://www.itscom.co.jp/forbiz/column/office-environment/1087)

#####DB関連
[https://26gram.com/what-is-database](https://26gram.com/what-is-database)
[https://www.acrovision.jp/career/?p=1912](https://www.acrovision.jp/career/?p=1912)

#####サーバー関連
[https://www.rworks.jp/system/system-column/sys-entry/16259/](https://www.rworks.jp/system/system-column/sys-entry/16259/)
[https://wa3.i-3-i.info/word14407.html](https://wa3.i-3-i.info/word14407.html)
[https://youtu.be/uTK55uaUJKQ](https://youtu.be/uTK55uaUJKQ)
[https://www.otsuka-shokai.co.jp/words/application-server.html](https://www.otsuka-shokai.co.jp/words/application-server.html)

#####MySQL関連
[https://www.sejuku.net/blog/9021](https://www.sejuku.net/blog/9021)

#####書籍
[はたらくプログラミング](https://www.amazon.co.jp/%E3%81%AF%E3%81%9F%E3%82%89%E3%81%8F%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0-%E5%AE%8C%E5%85%A8%E7%89%88-%E3%81%A8%E3%82%8A%E3%81%9F%E3%81%99/dp/4046801352/ref=sr_1_2_sspa?__mk_ja_JP=%E3%82%AB%E3%82%BF%E3%82%AB%E3%83%8A&dchild=1&keywords=%E3%81%AF%E3%81%9F%E3%82%89%E3%81%8F%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9F%E3%83%B3%E3%82%B0&qid=1616868282&sr=8-2-spons&psc=1&spLa=ZW5jcnlwdGVkUXVhbGlmaWVyPUFCWk9JRlRNNU1KTzImZW5jcnlwdGVkSWQ9QTAwMTIzOTEyUzA2RTFLS0dWSlFMJmVuY3J5cHRlZEFkSWQ9QTNPOUlaTjRSSEMzWFAmd2lkZ2V0TmFtZT1zcF9hdGYmYWN0aW9uPWNsaWNrUmVkaXJlY3QmZG9Ob3RMb2dDbGljaz10cnVl)
[サーバーのしくみ](https://www.amazon.co.jp/%E5%9B%B3%E8%A7%A3%E3%81%BE%E3%82%8B%E3%82%8F%E3%81%8B%E3%82%8A-%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%E3%81%AE%E3%81%97%E3%81%8F%E3%81%BF-%E8%A5%BF%E6%9D%91-%E6%B3%B0%E6%B4%8B-ebook/dp/B07NJ3F8VC/ref=sr_1_4?__mk_ja_JP=%E3%82%AB%E3%82%BF%E3%82%AB%E3%83%8A&dchild=1&keywords=%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%E3%81%AE%E4%BB%95%E7%B5%84%E3%81%BF&qid=1616868348&sr=8-4)
ABC197 一問一言解説(~D問題)

#[A - Rotate](https://atcoder.jp/contests/abc197/tasks/abc197_a)
基礎的な問題。Brainf**kでとても解きやすい問題である。特に、文字列の長さがわかっていて、とても短いことがありがたい。

#[B - Visibility](https://atcoder.jp/contests/abc197/tasks/abc197_b)
2次元配列の良い練習。解説では、マス(X,Y)から四方向にビームを出すようにして数えている(写真参照）。![スクリーンショット 2021-03-28 2.06.59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/916734/03eb87cb-5973-20ad-88fe-4236d023adb2.png)


#[C - ORXOR](https://atcoder.jp/contests/abc197/tasks/abc197_b)
**連続した区間**に注目。連続した区間で、Nは20以下なので、全探索できる。Pythonでは`itertools.product`が便利である。

#[D - Opposite](https://atcoder.jp/contests/abc197/tasks/abc197_d)
[複素平面で考えたり](https://atcoder.jp/contests/abc197/editorial/1025)、[ベクトルで考えたり](https://atcoder.jp/contests/abc197/editorial/1030)すると楽なようです。様々な解き方がある面白い問題。

#E,F問題
完全に理解してから書きます。

#参考文献
- [AtCoder公式解説](https://atcoder.jp/contests/abc197/editorial)
AWS 認定 データベース – 専門知識(DBS-C01)の学習内容

比較的新しい[AWS 認定 データベース – 専門知識](https://aws.amazon.com/jp/certification/certified-database-specialty/)の試験に向けて私が学習した内容を書きます。

## 前提条件
* RDB/NoSQLを利用したソフトウェア開発の経験あり
* RDBは性能向上を目的とした設定、クエリチューニングの経験あり
* RDBのマイグレーション、データベース移行の経験もあり

Web系開発が長いこともあり、データベースの経験も同様に長くあるのが私の前提となっています。

## 試験範囲の概要
[試験ガイド](https://d1.awsstatic.com/ja_JP/training-and-certification/docs-database-specialty/AWS-Certified-Database-Specialty_Exam-Guide.pdf)にも記載されている通り、以下のような分野、比重となっています。

|分野|試験における比重|
|---|---|
|分野 1: ワークロード固有のデータベース設計|26%|
|分野 2: 展開および移行|20%|
|分野 3: 管理および運用|18%|
|分野 4: 監視およびトラブルシューティング|18%|
|分野 5: データベースセキュリティ|18%|

## 学習内容
復習もかねて、以下の資料(Blackbelt等)を読み込みました。

### 資料など

[20190828 AWS Black Belt Online Seminar Amazon Aurora with PostgreSQL Compatibility](https://www.slideshare.net/AmazonWebServicesJapan/20190828-aws-black-belt-online-seminar-amazon-aurora-with-postgresql-compatibility-168930538)
[20190424 AWS Black Belt Online Seminar Amazon Aurora MySQL](https://www.slideshare.net/AmazonWebServicesJapan/20190424-aws-black-belt-online-seminar-amazon-aurora-mysql)
[AWS Black Belt Online Seminar 2016 AWS Database Migration Service](https://www.slideshare.net/AmazonWebServicesJapan/aws-black-belt-online-seminar-2016-aws-database-migration-service)
[AWS Black Belt Online Seminar 2017 Amazon ElastiCache](https://www.slideshare.net/AmazonWebServicesJapan/aws-black-belt-online-seminar-2017-amazon-elasticache-84060910)
[20200714 AWS Black Belt Online Seminar Amazon Neptune](https://www.slideshare.net/AmazonWebServicesJapan/20200714-aws-black-belt-online-seminar-amazon-neptune)
[AWS Black Belt Online Seminar 2017 Amazon DynamoDB](https://www.slideshare.net/AmazonWebServicesJapan/20170809-black-belt-dynamodb)
[AWS Black Belt Online Seminar 2018 Amazon DynamoDB Advanced Design Pattern](https://www.slideshare.net/AmazonWebServicesJapan/aws-black-belt-online-seminar-2018-amazon-dynamodb-advanced-design-pattern)
[AWS Schema Conversion Tool](https://docs.aws.amazon.com/ja_jp/SchemaConversionTool/latest/userguide)
[Amazon Quantum Ledger Database(QLDB)](https://d1.awsstatic.com/webinars/jp/pdf/services/20200609_AWS_BlackBelt_QLDB.pdf)

### 模擬試験など

模擬試験なども実施しました
[公式サンプル問題 10問](https://d1.awsstatic.com/ja_JP/training-and-certification/docs-database-specialty/AWS-Certified-Database-Specialty_Sample-Questions.pdf)
公式模擬問題(20問)
[Udemy | AWS Certified Database Specialty Practice Exams](https://www.udemy.com/course/aws-certified-database-specialty-practice-exams-dbs-c01/)

### その他
AWSマネジメントコンソールで、RDS等は多く触りました
特に、RDSパラメータについては、再起動の影響がでるもの、でないもの、そもそも変更できないもの
CloudWatchで見ていくべきメトリクス等、運用していく上でちゃんと考慮すべき内容を重点的に見直しました

## おわりに
試験には合格しましたが、

* データベースは多くのシステムで重要な役割を持つことが多い
* データベースが起因でトラブルが発生すると、原因分析や復旧が大変、かつ、時間をかけている状況ではないことが多い
* ユースケースや業務要件をしっかりくみ取ってデータベース設計しないと後が大変

という痛い目を見た経験もあるので、この機会は今までの見つめなおしができ、改めてよかったと思っています。
【Mac版】シェルスクリプトを作ってMySQLにラクラク接続する方法

## ターミナルからMySQLに接続する通常の方法
下記のコマンドを入力し**MySQL**に接続に接続する．

オプション`-p`と`[ パスワード ]`の間にはスペースを入れずに連続して指定

```
mysql -u [ ユーザ名 ] -p[ パスワード ]
```

## ユーザ名とパスワードを記述したシェルスクリプトからMySQLに接続
注意: セキュリティ面において個人使用のマシンに限定する事を推奨

デスクトップ上にシェルスクリプトを作成
```
touch ~/Desktop/mysql_start.command
```

シェルスクリプトに`[ ユーザ名 ]`と`[ パスワード ]`を指定

```mysql_start.command
#!/bin/bash
mysql -u [ ユーザ名 ] -p[ パスワード ]
killall Terminal
```

下記コマンドを実行して`.command`ファイルに実行権限を与える．

```
chmod u+x ~/Desktop/mysql_start.command
```

これで`mysql_start.command`をダブルクリックするだけで，**MySQL**に接続できるようになった．

## 知っておくと便利なMySQL接続オプション
あらかじめ`[ DB名 ]`や`[ ホスト名 ]`を指定してMySQLに接続する事も可能

|オプション|内容|
|:-:|:--|
|-D [ DB名 ]|DBを指定|
|-h [ ホスト名 ]|ホストを指定|

`u [ ユーザ名 ]`以外のオプションは順不同

```mysql_start.command
mysql -u [ ユーザ名 ] -p[ パスワード ] -D [ DB名 ] -h [ ホスト名 ]
```
C#(.NET)の書式指定

# C#(.NET)の書式指定

C#(.NET)において数値、日時等を書式を指定して文字列に変換(整形、フォーマット)する方法を整理します。
書式はカルチャに依存する為、実行環境のカルチャによって結果が異なります。
以下の例は日本語環境(`ja-JP`)で動作確認しました。


## 書式の指定方法

書式(フォーマット文字列)を指定して文字列への変換を行う方法はいくつかあります。

### `string.Format`メソッド

代表的な方法は`string.Format`メソッドを使用するものです。
フォーマット文字列を定数に定義して共有する等、応用がしやすくなります。

```csharp
string.Format("{0:N2}", 1234.56); // 1,234.56
```

### `ToString`メソッド

一部の組込型では`ToString`メソッドの引数に書式文字列を指定することが出来ます。
単一の値やオブジェクトを文字列に変換する場合に使用できます。

```csharp
(1234.56).ToString("N2"); // 1,234.56
```

### 文字列補間式

C# 6 で導入された文字列挿入(`$""`)を使用すると、リテラルのように文字列整形を記述することが出来ます。
フォーマット文字列を定数等で共有する必要が無い場合や、カルチャ指定が不要な場合には特に簡単に記述できます。

```csharp
$"{1234.56:N2}"; // 1,234.56
```


## 書式設定の種類

以下、書式設定の方法を簡単に紹介しています。
より詳細には後で紹介するMicrosoftの公式ドキュメント等をご参照ください。

### 書式指定無し

書式を指定しない場合(単に`ToString`メソッドを使用する場合等)、型に応じた一般的な書式で文字列に変換されます。
多くの組込型では、後述の標準書式指定子で`"G"`と同じ結果となります。

### 標準書式指定子

一般的に使用される書式を指定することが出来ます。

アルファベット1文字の書式指定子と、0～99の範囲で指定する精度指定子の組み合わせで書式を表現します。
書式指定子は 数値(`"N"`)、通貨(`"C"`) 等書式の種類を指定し、精度指定子は書式指定子によって小数部の桁数や有効桁数等を指定します。
精度指定子を省略した場合は書式指定子に応じた既定値が指定されたものとされます。

```csharp
string.Format("{0:N}", 1234.5678);  // 1,234.57
string.Format("{0:N1}", 1234.5678); // 1,234.6
string.Format("{0:N2}", 1234.5678); // 1,234.57
string.Format("{0:N3}", 1234.5678); // 1,234.568
```

### カスタム書式指定子

複数のカスタム書式指定子の組み合わせで、標準書式指定子では表現できない開発対象アプリケーションに固有の書式を作成することが出来ます。

```csharp
string.Format("{0:00000}", 1234.5678); // 01235
string.Format("{0:#,###.##}", 1234.5); // 1,234.5
string.Format("{0:#,###.00}", 1234.5); // 1,234.50
```


## 小数部の桁数

数値の小数部の桁数が書式で指定したものより大きい場合、小数部の桁数が書式に収まるように丸められますが、.NET Frameworkでは四捨五入で処理されます。
`Math.Round`メソッドが既定では銀行丸め[^1]を行うのとは動作が異なるので注意が必要です。[^2]

```csharp
string.Format("{0:N3}", 1.2345); // 1.235
string.Format("{0:N3}", Math.Round(1.2345, 3)); // 1.234
```

[^1]: 銀行丸め: 端数が5の場合に、丸めた後の末尾の数値が偶数になるように丸める方法。
[^2]: さらにややこしいことに、.NET Core 2.1以降では銀行丸めに統一されたそうです。この辺り動作確認が取れたら追記する予定です。

## カルチャの指定

`string.Format`メソッドや一部の組込型の`ToString`メソッドには`IFormatProvider`オブジェクトを引数にとるオーバーロードが用意されています。
これにカルチャ(`CultureInfo`)を渡して任意のカルチャを対象にした書式指定が出来ます。

```csharp
string.Format(new CultureInfo("ja-JP"), "{0:C}", 1234.56); // ¥1,235
string.Format(new CultureInfo("en-US"), "{0:C}", 1234.56); // $1,234.56
```

文字列補間式は`FormattableString`型の変数に代入することで、カルチャを指定した書式指定ができます。[^3]

[^3]: @juner 氏にコメントでご指摘頂きました。氏のコメントでも紹介されていますので、是非ご参照ください。

```csharp
FormattableString format = $"{1234.56:C}";
format.ToString(new CultureInfo("ja-JP")); // ¥1,235
format.ToString(new CultureInfo("en-US")); // $1,234.56
```

この場合、`format`変数は`FormattableString`型を明示する必要があります。
`var`で宣言した場合、単に文字列補完式により整形された文字列(`string`)が代入されます。


## 参考

以下の公式ドキュメントを参考にしました。

https://docs.microsoft.com/ja-jp/dotnet/standard/base-types/formatting-types

https://docs.microsoft.com/ja-jp/dotnet/api/system.string.format?view=net-5.0
ABC197 振り返りメモ(D問題まで)

#結果
ABDの3完で, レート変化は<font color="Maroon">704</font>→<font color="Maroon">729</font>(+25)

#[A問題 ( Rotate )](https://atcoder.jp/contests/abc197/tasks/abc197_a)
###概要
> 3文字の文字列Sの, 先頭の文字を末尾に持っていったときにできる文字列を出力せよ.

###方針
問題の通りにやる.
汎用的な解法として, rotate関数を使うものもある.

C++ での実装例は以下のようになる.

```cpp:a.cpp
#include <bits/stdc++.h>
using namespace std;

int main() {
    string S;
    cin >> S;
    cout << S[1] << S[2] << S[0] << endl;
    return 0;
} 
```

#[B問題 ( Visibility )](https://atcoder.jp/contests/abc197/tasks/abc197_b) 
###概要
> 障害物ありの二次元平面で, 与えられた位置の上下左右方向にある障害物 ( または壁 )までの距離の合計を求める.

### 方針

上下左右, 全ての方向に対して障害物までの距離を数えていけば良い.
似たような操作を4回行わなくても良いように工夫すると, 下のような実装になる.


```cpp:b.cpp
#include <bits/stdc++.h>
using namespace std;
#define rep(i,n) for (long long i = 0; i < (n); i++)
using ll = long long;

ll dx[] = {-1, 0, 1, 0};
ll dy[] = {0, -1, 0, 1};

int main() {
    ll H, W, X, Y;
    cin >> H >> W >> X >> Y;
    vector<string> S(H);
    rep(i, H) cin >> S[i];
    X--; Y--;
    ll ans = 1;
    rep(i, 4) {
        ll x = X;
        ll y = Y;
        while (1) {
            x += dx[i];
            y += dy[i];
            if (x >= H || y >= W || x < 0 || y < 0) break;
            if (S[x][y] == '#') break;
            ans++;
        }
    }
    cout << ans << endl;
    return 0;
} 
```

#[C問題 ( ORXOR )](https://atcoder.jp/contests/abc197/tasks/abc197_c)
###概要
> 略

### 方針
N 個の要素間の間に仕切りを置くか置かないかを全通り探索する.
N 個の要素間は N - 1 個あるので, 全部で 2 ^ ( N - 1 ) 通り探索しないといけない.
2の累乗数通り探索する場合, bit全探索をすると良い.
そして, 仕切りを置くタイミングで, XOR を更新する. 
最後に XOR を更新するのも忘れないようにする.

C++ での実装例は以下のようになる.

```cpp:c.cpp
#include <bits/stdc++.h>
using namespace std;
#define rep(i,n) for (long long i = 0; i < (n); i++)
using ll = long long;

const ll LINF = (1LL << 60) - 1;

int main() {
    ll n; cin >> n;
    vector<ll> a(n);
    rep(i, n) cin >> a[i];
    ll ans = LINF;
    for (ll bit = 0; bit < (1 << n-1); bit++) {
        ll now = 0;
        ll o = 0;
        for (ll i = 0; i < n; i++) {
            o |= a[i];
            if (bit & (1 << i)) {
                now ^= o;
                o = 0;
            }
        }
        now ^= o;
        ans = min(ans, now);
    }
    cout << ans << endl;
    return 0;
} 
```

#[D問題 (  Opposite )](https://atcoder.jp/contests/abc197/tasks/abc197_d)
###概要
> 正n角形の頂点の1つ(p.0)の座標と, その反対側にある頂点(p.2/n)の座標が与えられるので, p1 の座標を計算する.

### 方針
複素数を用いて計算すると簡単である.
以下の図のようになるので, 中点に当たる複素数を mid とすると, mid + (p0 - mid) * ( cos(2π/n), sin(2π/n) )　を計算すれば良いことが分かる.
![スクリーンショット 2021-03-28 1.26.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/981458/a1af3f82-9680-a23c-bbc6-6bf9079710f0.png)


C++ での実装例は以下のようになる.

```cpp:d.dpp
#include <bits/stdc++.h>
using namespace std;
using ll = long long;

using C = complex<double>; // 追加
const double PI = acos(-1);

int main() {
    ll n; cin >> n;
    double x, y, x_, y_;
    cin >> x >> y >> x_ >> y_;
    C s = C(x, y);
    C t = C(x_, y_);
    C mid = (s + t) / 2.0;
    double rad = 2 * PI / n;
    C r(cos(rad), sin(rad));
    C ans = mid + (s - mid) * r;
    cout << fixed << std::setprecision(15) << ans.real() << endl;
    cout << fixed << std::setprecision(15) << ans.imag() << endl;
    return 0;
}

```
動的アクションで強調表示パネルのアクション（ボタン）をプロファイルごとに設定する方法

##動的アクションによる強調表示パネルのアクションの制御を紹介します。
今回はプロファイル「標準ユーザ」に「活動の記録」アクションを表示させないようにします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/694683/1d647aee-b830-a603-47b2-7d633e777b26.png)


#####１.「動的アクションのアップグレード」の「アップグレードに対するお問い合わせ」をクリックして動的アクションを利用できるようにします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/694683/51db7d1f-7731-46b9-5867-2eb725b44fc8.png)

#####2.「活動の記録」アクションを選択して「検索条件を追加」をクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/694683/d35f24a1-7c3a-a43d-2a62-e429f2ec7087.png)

#####3.条件種別の詳細の「選択」をクリックします。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/694683/4c6d8c73-b143-b141-bb24-bccb1b6d3047.png)

#####4.「ユーザ」→「プロファイル」から「プロファイル名」を選択します。演算子を「不等号」、値を「標準ユーザ」に設定して完了を押して保存します。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/694683/269c1fcf-2578-e1f8-0b36-e2de708cc342.png)

#####5.プロファイルが「標準ユーザ」のユーザでログインすると「活動の記録」が表示されないことが確認できます。![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/694683/3beb219c-c82c-d165-ca85-839641c658d6.png)
Cognito と Amplify の密結合について思うこと

# はじめに

なんでこうなってるんだということに出会ったので、ここで思ったことを書き記す。 あくまで私見であり、結論は特に出してない。

きっかけは [amazon-cognito-identity-js](https://www.npmjs.com/package/amazon-cognito-identity-js) のGithubページを開いたこと。 これは未だにnpmで公開されているけど、実はリポジトリが当初と変わっている。

## 変更前

> https://github.com/amazon-archives/amazon-cognito-identity-js

## 変更後

> https://github.com/aws-amplify/amplify-js/tree/main/packages/amazon-cognito-identity-js

と、何故か Amplify のサブセットの位置に再配置されてしまっている。

引き続き、`npm` や `yarn` で `amazon-cognito-identity-js` を入れることはでき、この場合に Amplify が入ってくることはないのだが、まるで Cognito が Amplify のサービスの完全な一部分であると捉えられても仕方ない構成になっている。


# 思うこと

**何故混ぜた** である。　以下の Issue ですでにやり取りされているし、分離する気はないようだが・・・

https://github.com/aws-amplify/amplify-js/issues/3635

AWSはいろいろなサービスをリリースしていて、これを組み合わせて使えることがメリットであると考えている。 しかし、このような方法を推奨してしまうと、折角出した個別のサービスを無駄に密結合にしているようにしか見えない。  
Amplify の開発を進めてその利用を促したいのは分かるが、これを見て「将来的には Cognito は Amplify でしか使えないようになるのではないか」という疑念を持った。 他にもIssue内から意見を拾うと、「Cognito だけしか使わないソースコードの中に Amplify という文字列が出てきて、開発者を混乱させる」といったことも考えられる。

さらに言えば、Amplify での多言語対応ログインUIは作成されているにも関わらず、Cognito Hosted UI のログインUIは問題が認識されてから2年以上（リリースから考えるともっと長期間？）多言語対応が行われていない。 それこそ、一般ユーザーに使わせる上では真っ先に需要に答えるべき場所だと思うのだが。

https://forums.aws.amazon.com/thread.jspa?threadID=301920

これに対しても「Amplify ではできるから」と返されるかもしれないが、Amplify には Amplify の成約があり、Cognito という IDaaS を単独で使いたいという需要はかなりあるはずである。

https://github.com/aws-amplify/amplify-js/issues/3495

もしかして、Cognito そのものにかけるリソースが少ないのかもしれず、それを Amplify でカバーしようとしているのかもしれないが、そうすると Cognito を使うことを辞めるべきなのだろうか、とも考えてしまう。

Amplify + Cognito でガッツリ使うというのであれば良いが、そうでない場合は Cognito だけでなく IDaaS である Firebase Authentication か Auth0 あたりも触っておいたほうが良いのかもしれない。
WebViewでウェブサイトを表示する【Swift】

Swift学習2日目、自分用の備忘録です。

インディケーターを表示後、ロードが完了したらWebサイトを表示するコードです。

## ストーリーボードに以下を追加
①Activity Indicator View：ロード中に表示するインディケーター
②Toolbar：戻るボタンと進むボタンを配置するためのツールバーを下部に設置
③Bar Button Item：戻るボタンと進むボタンをToolbar情に配置
④Fixed Space Bar Button Item：戻るボタンと進むボタンの間にスペースを配置

## コード

```swift
import UIKit
import WebKit // ライブラリをインポート

class ViewController: UIViewController, WKNavigationDelegate { // デリゲートを追加
    
    @IBOutlet weak var indicater: UIActivityIndicatorView! // ローディングのインディケーターを追加
    @IBOutlet weak var toolbar: UIToolbar! // 戻るボタンを並べたツールバー
    var webview = WKWebView()
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        // ウェブビューの大きさを決める
        webview.frame = CGRect(x: 0, y: 0, width: view.frame.size.width, height: view.frame.size.height - toolbar.frame.size.height)
        
        // Viewにウェブビューを追加
        view.addSubview(webview)
        
        webview.navigationDelegate = self
        
        // URLをロード
        let url = URL(string: "https://text.com/")
        let request = URLRequest(url: url!)
        webview.load(request)
        
        indicater.layer.zPosition = 2 // インディケーターをウェブビューより手前に配置
    }

    // 読み込みが開始されたときに呼ばれるデリゲートメソッド
    func webView(_ webView: WKWebView, didCommit navigation: WKNavigation!) {
        indicater.isHidden = false
        indicater.startAnimating()
    }

    // ロードが完了したときに呼ばれるデリゲートメソッド
    func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
        indicater.isHidden = true
        indicater.stopAnimating()
    }
   
    @IBAction func back(_ sender: Any) {
        webview.goBack() // 戻るボタン
    }
    
    @IBAction func go(_ sender: Any) {
        webview.goForward() // 進むボタン
    }
    
}


```
【VBA】一瞬でシートのコピー、名前変更が出来る方法

今回は、簡単にシートを複製するマクロを作ります。

最初に、ソースコードを記載します。

```vb.シートのコピー
Sub シートをコピーする()

Dim ws As Worksheet
Set ws = ThisWorkbook.Sheets("見積書")

Dim wsName As String
wsName = ws.Cells(3, 1).Value

' 同名のワークシートがないことをチェック
If nameCheckFlag(wsName) = True Then
    
    MsgBox "同名のシートが存在するため、シートを作成できません。"

Else
    ' 「見積書」シートをコピーして一番右に追加する。
    ws.Copy After:=Sheets(Sheets.Count)

    ' 追加したシートがActiveになっているので、ActiveSheetを通じて名前を設定する。
    ActiveSheet.name = wsName
    
End If

' 見積書シートをアクティブにする
ws.Activate

End Sub

' 同名のワークシートがないかチェックする関数
Function nameCheckFlag(wsName As String) As Boolean
    Dim ws As Worksheet
    
    For Each ws In Worksheets
        If wsName = ws.name Then
            nameCheckFlag = True
            Exit For
        Else
            nameCheckFlag = False
        End If
    Next ws

End Function


```

今回は、以下のサンプルシートを使用します。
![サンプル](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1242278/6f24defa-9260-e311-8767-896500af5125.jpeg)

マクロを動かすと、見積書シートがコピーされ、末尾に会社名でシートがコピーされます。

![サンプル2](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1242278/4b265e76-25d8-ff4e-1baf-97cdf03677e2.jpeg)

それでは、詳細について書いていきます。

>Dim ws As Worksheet
>Set ws = ThisWorkbook.Sheets("見積書")

こちらで、コピー対象のwsを変数に格納しています。

>Dim wsName As String
>wsName = ws.Cells(3, 1).Value

ここでは、コピーしたシートの名前を取得してます。
取得名は会社名としたいので、列は3、行は1を指定しています。

>If nameCheckFlag(wsName) = True Then

こちらで、同名のシートがないか確認しています。
同名のシートが存在していた場合は、MsgBoxにてエラーメッセージを表示します。

```
Function nameCheckFlag(wsName As String) As Boolean
    Dim ws As Worksheet
    
    For Each ws In Worksheets
        If wsName = ws.name Then
            nameCheckFlag = True
            Exit For
        Else
            nameCheckFlag = False
        End If
    Next ws

End Function

```

上記が同名のシートが存在するかチェックする関数です。

```
For Each ws In Worksheets
        If wsName = ws.name Then
            nameCheckFlag = True
            Exit For
        Else
            nameCheckFlag = False
        End If
    Next ws
```

For Eachを使用し、全てのワークシートを1ずつチェックし、
同名なものが1つでもあった場合はTrueを返し、Exit Forでループ終了しています。

>ws.Copy After:=Sheets(Sheets.Count)

上記では、コピーしたシートを末尾に設置します。

>ActiveSheet.name = wsName

コピーすると、コピーされたシートがアクティブになるため、
会社名を格納したwsNameでシート名を変更します。

>ws.Activate

コピーとシート名の変更が完了したら、アクティブシートを見積書に戻してます。

以上が、シートを複製するマクロになります。
Reverse Geocoder(逆ジオコーダー) android × kotlin

<h1>Reverse Geocoder(逆ジオコーダー)</h1>
<p>kotlinで書いている記事が少なかったので書き残して起きます。</p>
<p>逆ジオコーデイングする上で少し沼ってしまったので</p>
<p>誰かの参考になればいいかなと思っています。</p>
<p>＊自分は実務経験がない開発者なので間違っている場合があると思いますが</p>
<p>そこら辺はご容赦ください。</p>
<h2>環境</h2>
<dl>
  <dt>言語</dt>
  <dd>kotlin</dd>
  <dt>フレームワーク</dt>
  <dd>Android Studio 4.1.2</dd>
</dl>
<h2>やり方</h2>
<h4>事前準備</h4>
<p>経度緯度を取得しておく</p>
<p>latitude（緯度）とlongitude(経度)</p>
<h4>逆ジオコーダー</h4>
```kotlin.MapActivity.kt
fun getAddress(latitude: Double, longitute: Double) {
        val strAddr = StringBuffer()
        val gcoder = Geocoder(this, Locale.getDefault())
        try {
            val lstAddrs = gcoder.getFromLocation(latitude, longitute, 1)
            for (addr in lstAddrs) {
                val idx = addr.maxAddressLineIndex
                for (i in 0..idx) {
                    strAddr.append(addr.getAddressLine(i))
                    Log.v("addr", addr.getAddressLine(i))
                }
            }
            val newStr = strAddr.toString()
            val names = newStr.split(" ".toRegex()).toTypedArray()
            //↓変更必要(geocoderText)
            geocoderText.setText(names[1])
            Toast.makeText(this, names[1], Toast.LENGTH_LONG).show()
        } catch (e: IOException) {
            e.printStackTrace()
        }
    }
```
<p>後はこいつを呼び出せば使えます</p>
```kotlin.MapActivity.kt
getAddress(latitude,longitude)
```
<p>latitude（緯度）とlongitude(経度)の部分は</p>
<P>最初に説明した通り、事前に準備が必要です。</p>
UITableViewで指定した位置までスクロールさせたいのにクラッシュした

任意のセルまでスクロールさせたい時は、下記コードを使うと思います。


```swift
      tableView.scrollToRow(at: indexPath, at: .top, animated: false)
```


…が、これだと、クラッシュすることがあった！
そんな時は、ちゃんとセルが存在しているか疑ってみてください。

自分はセルが0件の場合もセクションを表示して、そのセクションまでスクロールさせたいケースがあったのですが、上記のコードだとindexPathの場所に移動させるので、セルがなかった場合にクラッシュしました。

任意のセクションまでスクロールさせることができれば良いのですが、Swiftにはそのような機能は今のところありません。

~~なので、indexPath部分に`NSNotFound`を指定してあげれば、クラッシュせず、スクロールされます。~~
~~```tableView.scrollToRow(at: NSNotFound, at: .top, animated: false)
```~~
※コメントいただいたので、修正しました！下記のように指定してあげるのが適切です。

NSNotFoundを指定したindexPathを渡してあげれば、セルの行数やセクションが0個でもクラッシュせず、スクロールされます。


```swift
if tableView.numberOfSections > 0 {
    let indexPath = IndexPath(at: NSNotFound, section: 0)
    tableView.scrollToRow(at: indexPath, at: .top, animated: false)
}
```
section数がいくつもあり、indexを指定したい場合はindexPathを引数でとって、`section: 0`の部分を適宜変えてくださいね。
sectionのindexPathをindexという引数でとるとしたら、こんなコードになるかと思います。

```swift
    let indexPath = IndexPath(at: NSNotFound, section: index)
    tableView.scrollToRow(at: indexPath, at: .top, animated: false)
```


[公式ドキュメント](https://developer.apple.com/documentation/uikit/uitableview/1614997-scrolltorow)にも`NSNotFound is a valid row index for scrolling to a section with zero rows.`と書いてあるので、推奨された方法といえます。