OmniAICreator/Qiita-1.07M huggingface dataset:
【ABC285_D】 DFS(深さ優先探索)で解いてみた 【C++】

[abc285のD問題](https://atcoder.jp/contests/abc285/tasks/abc285_d)をDFS(深さ優先探索)を使って解いてみました。
言語はC++です。

- [UnionFindを使った解き方はこちら](https://qiita.com/Sakasu/items/28d153111042c9562bc7 "")
- [BFS(幅優先探索)を使った解き方はこちら](https://qiita.com/Sakasu/items/2fb79169367d650d64a4 "")

# Point

1. **a → b → c → aと一巡したらダメ**そう
    * グラフ理論でいうところの**サイクル(閉路)があるかどうかを検出**
2. **探索した頂点をmemo**することでTLE対策
3. **DFS**(深さ優先探索)で全頂点から探索してサイクルがあるかを検出
    * **既にvisitedな頂点に再度訪問 -> サイクル有り**
    ```    
       a------>b------>c　　 既に訪問済みの頂点aに対し、aに再訪問するとサイクルができる
       ^---２回目のa---|
    ```      
4. 解けました！

# コード例

```c++:d_dfs.cpp
#include <iostream>
#include <string>
#include <vector>
#include <unordered_map>
#include <atcoder/all>
using namespace std;
using namespace atcoder;
#define rep(i, a, b) for (int i = a; i < b; i++)

int n;
unordered_map<string, bool> memo;
unordered_map<string, int> visited;
using Graph = unordered_map<string, vector<string>>;
Graph G;

bool dfs(string s){
    memo[s] = true; //探索した全頂点を記録
    if(visited[s]) return true; //既に行きがけで探索済みの頂点に再度訪れた場合、サイクルが出来ているのでtrue
    //ex. a---->b---->c---->aは  最初のaでvisited[a]=trueなので、
    //    a---->b---->c 二回目のaではサイクルができる
    //    ^-----------|
    bool closed = false;
    //行きがけの往路だけtrueにしておく
    //a----->b  visited[b] = true;
    visited[s] = true;
    for(auto t : G[s]){
        if(dfs(t)) closed = true;
    }
    //行きがけの復路はfalse
    //a----->b  visited[b] = false;
    //^------| return
    visited[s]=false;
    return closed;
}

int main(){
    cin>>n;
    vector<string> s(n), t(n);
    rep(i,0,n){
        cin >> s[i] >> t[i];
        //s->tのグラフを作成
        G[s[i]].emplace_back(t[i]);
    }
    rep(i,0,n){
        string start = s[i];
        if(memo[start]) continue;  //既にdfsで探索済み頂点は無視
        bool closed = dfs(start);
        if(closed){
            cout << "No" << endl; 
            return 0;
        }
    }
    cout << "Yes" << endl;
    return 0;
}
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2404591/27f9c88b-74b0-4b03-750e-b1055c19a136.png)

解けました！
AWS CDK - Environment

# Environment

環境 (env) は、スタックがデプロイされる AWS アカウントと AWS リージョンを表します。

AWS CDK は、現在の AWS CLI プロファイルでデフォルトのリージョンとアカウントを選択します。

デフォルトとは異なる値のセットを指定することで、明示的に手動で環境を上書きすることができます。

# 1.作成前に AWSアカウントと AWSリージョンを決定する

AWSアカウントと AWSリージョンをハードコーディングすると、スタックは常にその特定のアカウントとリージョンにデプロイされます。

次の例は、東京リージョンと大阪リージョンに作成する例です。

```python:app.py
#!/usr/bin/env python3

import aws_cdk as cdk

from pysample.pysample_stack import PysampleStack

app = cdk.App()
env_tokyo = cdk.Environment(account="123456789012", region="ap-northeast-1")
env_osaka = cdk.Environment(account="123456789012", region="ap-northeast-3")
PysampleStack(app, "PysampleStack1", env=env_tokyo)
PysampleStack(app, "PysampleStack3", env=env_osaka)

app.synth()
```

`cdk synth` を実行する場合は、次のように ID を指定する必要があります。

```cdk
cdk synth PysampleStack1
cdk synth PysampleStack3
```

`cdk deploy` で全てのスタックをデプロイする場合は、`--all`、
特定のスタックをデプロイする場合は、ID を指定します。

```
cdk deploy --all

cdk deploy PysampleStack1
cdk deploy PysampleStack3
```

# 2.作成時に AWSアカウントと AWSリージョンを決定する

スタックを別の AWS アカウントと AWS リージョンにデプロイできるようにしつつ、作成時に AWSアカウントと AWSリージョンを決定するには、AWS CDK CLI が提供する 2 つの環境変数、`CDK_DEFAULT_ACCOUNT` 及び `CDK_DEFAULT_REGION`を利用します。
これらの変数は、`AWS--profile` オプションを使用して指定されたプロファイル、または指定しない場合はデフォルトプロファイルに基づいてデプロイされます。

```app.py
#!/usr/bin/env python3

import aws_cdk as cdk
import os

from pysample.pysample_stack import PysampleStack

app = cdk.App()
PysampleStack(app, "dev", env=cdk.Environment(
    account=os.environ["CDK_DEFAULT_ACCOUNT"],
    region=os.environ["CDK_DEFAULT_REGION"]))

app.synth()
```

# 3.2 つの追加の環境変数をサポートするようにスタックを記述して、作成時にオーバーライドする

有効な式を使用して、好きなように env を設定できます。
たとえば、2 つの追加の環境変数をサポートするようにスタックを記述して、合成時にアカウントとリージョンをオーバーライドできるようにすることができます。
次のスタックの環境では、代替の環境変数が設定されている場合に使用されます。 
設定されていない場合、AWS CDK によって提供されるデフォルトの環境にフォールバックします。

```app.py
#!/usr/bin/env python3

import aws_cdk as cdk
import os

from pysample.pysample_stack import PysampleStack

PysampleStack(app, "dev", env=cdk.Environment(
    account=os.environ.get("CDK_DEPLOY_ACCOUNT", os.environ["CDK_DEFAULT_ACCOUNT"]),
    region=os.environ.get("CDK_DEPLOY_REGION", os.environ["CDK_DEFAULT_REGION"])

app.synth()
```
Databricks on AWSのPrivateLink環境でクロスアカウントS3アクセスに苦労した話

こちらでPrivateLink環境を構築し、

https://qiita.com/taka_yayoi/items/15426201a982e0922b5f

こちらでクロスアカウントのS3バケットにアクセスできるように設定しました。ここまででも結構な道のり。

https://qiita.com/taka_yayoi/items/e7e86c02c8dcb567c717

問題なく接続できるだろうと思ったらエラーに。

```py:Python
display(dbutils.fs.ls("s3a://ty-databricks-cross-account-bucket"))
```

![Screenshot 2023-01-22 at 14.18.22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/51e6b37f-87ca-1a81-9372-0ab2b57d7b96.png)

```
org.apache.hadoop.net.ConnectTimeoutException: Instantiate shaded.databricks.org.apache.hadoop.fs.s3a.auth.AssumedRoleCredentialProvider on : com.amazonaws.SdkClientException: Unable to execute HTTP request: Connect to sts.amazonaws.com:443 [sts.amazonaws.com/54.239.21.217] failed: connect timed out
```

インスタンスプロファイルも設定して、クラスターのSpark設定も以下のようになっています。

```
fs.s3a.aws.credentials.provider org.apache.hadoop.fs.s3a.auth.AssumedRoleCredentialProvider
spark.databricks.hive.metastore.glueCatalog.enabled true
fs.s3a.assumed.role.arn arn:aws:iam::<S3バケットがあるAWSアカウントID>:role/bucket-owner-acct-s3-access-role
```

エラーメッセージをよく見てみると、`Unable to execute HTTP request: Connect to sts.amazonaws.com:443 [sts.amazonaws.com/54.239.21.217] failed: connect timed out`であれっと。STSのリージョナルエンドポイントも設定しているのになぜグローバルURLにアクセスしているのか。

解決策は[Troubleshoot regional endpoints](https://docs.databricks.com/administration-guide/cloud-configurations/aws/customer-managed-vpc.html#troubleshoot-regional-endpoints)に。Spark設定で明示的にリージョナルエンドポイントを参照するようにすることで解決しました。以下の2行を追加。リージョンは`ap-northeast-1`です。

```
spark.hadoop.fs.s3a.endpoint https://s3.ap-northeast-1.amazonaws.com
spark.hadoop.fs.s3a.stsAssumeRole.stsEndpoint https://sts.ap-northeast-1.amazonaws.com
```

これで無事アクセスできました。
![Screenshot 2023-01-22 at 14.24.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/5564dcfa-d9fb-c718-e80a-0dab466dd96c.png)


### Databricks 無料トライアル

[Databricks 無料トライアル](https://databricks.com/jp/try-databricks)
cscの作法 その290

# 概要
cscの作法、調べてみた。
CallNextHookEx使ってみた。

# 参考にしたページ

https://qiita.com/rbtnn/items/74d0b1438776cca1c1ea


# サンプルコード

```
using System;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using System.ComponentModel;

namespace Testhook
{
	class MainForm : Form {
		[DllImport("user32.dll", SetLastError = true)]
		public static extern IntPtr SetWindowsHookEx(int hookType, HookHandler hookDelegate, IntPtr module, uint threadId);
		[DllImport("user32.dll", SetLastError = true)]
		public static extern bool UnhookWindowsHookEx(IntPtr hook);
		[DllImport("user32.dll")]
		public static extern int CallNextHookEx(IntPtr hook, int code, IntPtr message, IntPtr state);
		[StructLayout(LayoutKind.Sequential)]
		public class KBDLLHOOKSTRUCT {
			public uint vkCode;
			public uint scanCode;
			public KBDLLHOOKSTRUCTFlags flags;
			public uint time;
			public UIntPtr dwExtraInfo;
		}
		[Flags]
		public enum KBDLLHOOKSTRUCTFlags : uint {
			LLKHF_EXTENDED = 0x01,
			LLKHF_INJECTED = 0x10,
			LLKHF_ALTDOWN = 0x20,
			LLKHF_UP = 0x80,
		}
		public delegate int HookHandler(int code, IntPtr message, IntPtr state);
		HookHandler hookDelegate;
		IntPtr hook;
		public MainForm() {
			const int KEYBOARD_LL = 13;
			hookDelegate = new HookHandler(OnHook);
			IntPtr hMod = Marshal.GetHINSTANCE(System.Reflection.Assembly.GetExecutingAssembly().GetModules()[0]);
			hook = SetWindowsHookEx(KEYBOARD_LL, hookDelegate, hMod, 0);
			if (hook == IntPtr.Zero)
			{
				int errorCode = Marshal.GetLastWin32Error();
				throw new Win32Exception(errorCode);
			}
		}
		protected override void OnClosing(CancelEventArgs e) {
			base.OnClosing(e);
			if (hook != IntPtr.Zero)
			{
				UnhookWindowsHookEx(hook);
			}
		}
		int OnHook(int nCode, IntPtr wParam, IntPtr lParam) {
			KBDLLHOOKSTRUCT kb = (KBDLLHOOKSTRUCT) Marshal.PtrToStructure(lParam, typeof(KBDLLHOOKSTRUCT));
			Console.WriteLine("vkCode={0}", kb.vkCode);
			if (kb.vkCode == 32)
			{

				return 1;
			}
			else
			{
				return CallNextHookEx(hook, nCode, wParam, lParam);
			}
		}
	}
	static class TestHook {
		[STAThread]
		static void Main(string[] args) {
			Application.Run(new MainForm());
		}
	}
}





```



以上。
cscの作法 その289

# 概要
cscの作法、調べてみた。
SendInput使ってみた。

# 参考にしたページ

https://qiita.com/kob58im/items/ca3b61e72111dfbab8a8


# サンプルコード

```
using System;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Windows.Forms;

class MainForm : Form {
	private static class NativeMethods {
		[DllImport("user32.dll", SetLastError = true)]
		public extern static void SendInput(int nInputs, Input[] pInputs, int cbsize);
		[DllImport("user32.dll", EntryPoint = "MapVirtualKeyA")]
		public extern static int MapVirtualKey(int wCode, int wMapType);
	}
	[StructLayout(LayoutKind.Sequential)]
	private struct POINT {
		public int x;
		public int y;
	}
	[StructLayout(LayoutKind.Sequential)]
	struct MouseInput {
		public int X;
		public int Y;
		public int Data;
		public int Flags;
		public int Time;
		public IntPtr ExtraInfo;
	}
	[StructLayout(LayoutKind.Sequential)]
	struct KeyboardInput {
		public short VirtualKey;
		public short ScanCode;
		public int Flags;
		public int Time;
		public IntPtr ExtraInfo;
	}
	[StructLayout(LayoutKind.Sequential)]
	struct HardwareInput {
		public int uMsg;
		public short wParamL;
		public short wParamH;
	}
	[StructLayout(LayoutKind.Sequential)]
	struct Input {
		public int Type;
		public InputUnion ui;
	}
	[StructLayout(LayoutKind.Explicit)]
	struct InputUnion {
		[FieldOffset(0)]
		public MouseInput Mouse;
		[FieldOffset(0)]
		public KeyboardInput Keyboard;
		[FieldOffset(0)]
		public HardwareInput Hardware;
	}
	private const int KEYEVENTF_EXTENDEDKEY = 0x0001;
	private const int KEYEVENTF_KEYUP = 0x0002;
	private const int KEYEVENTF_SCANCODE = 0x0008;
	private const int KEYEVENTF_UNICODE = 0x0004;
	private const int MAPVK_VK_TO_VSC = 0;
	TextBox txt;
	MainForm() {
		Button btn = new Button();
		btn.Location = new Point(130, 130);
		btn.Size = new Size(70, 30);
		btn.Text = "sendkey";
		btn.Click += btn_Click;
		Controls.Add(btn);
		txt = new TextBox();
		txt.Location = new Point(30, 30);
		txt.Size = new Size(100, 30);
		txt.Text = "koko mite";
		Controls.Add(txt);
	}
	private void btn_Click(object sender, EventArgs e) {
			SendInputKeyPressAndRelease(Keys.Tab);
			SendInputKeyPressAndRelease(Keys.A);
		}
	private static void SendInputKeyPressAndRelease(Keys key) {
		Input[] inputs = new Input[2];
		int vsc = NativeMethods.MapVirtualKey((int) key, MAPVK_VK_TO_VSC);
		inputs[0] = new Input();
		inputs[0].Type = 1;
		inputs[0].ui.Keyboard.VirtualKey = (short) key;
		inputs[0].ui.Keyboard.ScanCode = (short) vsc;
		inputs[0].ui.Keyboard.Flags = 0;
		inputs[0].ui.Keyboard.Time = 0;
		inputs[0].ui.Keyboard.ExtraInfo = IntPtr.Zero;
		inputs[1] = new Input();
		inputs[1].Type = 1;
		inputs[1].ui.Keyboard.VirtualKey = (short) key;
		inputs[1].ui.Keyboard.ScanCode = (short) vsc;
		inputs[1].ui.Keyboard.Flags = KEYEVENTF_KEYUP;
		inputs[1].ui.Keyboard.Time = 0;
		inputs[1].ui.Keyboard.ExtraInfo = IntPtr.Zero;
		NativeMethods.SendInput(inputs.Length, inputs, Marshal.SizeOf(inputs[0]));
	}
	[STAThread]
	static void Main(string[] args) {
		Application.Run(new MainForm());
	}
}





```


以上。
AWSのここが便利(フリーランスエンジニアから教えてもらった使える知識)

<h3>Cloud9(クラウドナイン)</h3>

<ul>
<li>クラウドサービスの統合開発環境(IDE)</li>
<li>ブラウザからどこでもコードを編集、実行、デバッグできる。</li>
<li>環境構築の手間が省ける</li>
<li>稼働時間のみ課金されるのでお安い(為替状況にもよるが、月100時間稼働で$3くらい)</li>
</ul>

<h3>CloudFront(クラウドフロント)</h3>
<ul>
<li>コンテンツデリバリーネットワーク(CDN)
<br>※CDNとは：地理的分散されたサーバーを使用することで、Webコンテンツの配信を高速化する。　(関連：オリジンサーバー、エッジサーバー)</li>
</ul>

<h3>S3(エススリー)</h3>

<ul>
<li>オブジェクトストレージサービス(どこからでもデータの保存と取得ができるストレージサービス)</li>
<li>HTML,CSS,imageなどを保存</li>
<li>格納容量無制限、従量課金制</li>
</ul>

<h3>Lightsail(ライトセイル)</h3>
<ul>
<li>仮想プライベートサーバー(VPN)</li>
<li>Webサイトやアプリケーション環境を数クリックで構築可能(必要な機能が専用管理画面でシンプルに管理できる)</li>
<li>月額制
<br>例)WordPressを使ったWebサイトを作りたい場合、インスタンス(サーバー)作成時にWPを選択すればすぐ作れる</li>
</ul>

<h3>その他メモ</h3>
<ul>
<li><strong>CloudFrontとS3を組み合わせると…</strong><br>サーバーレス＆可用性・耐久性の高い静的なウェブサイトの公開が可能(静的ウェブホスティング、S3だけでも可能だがCDNと組み合わせると最強)</li>
<br>
<li><strong>Cloud9とVS Codeの違い例えるなら</strong><br>ExcelとGoogleスプレッドシートのような違い。Colud9は共同編集可能(VS Codeはプラグインで可能)。他のAWSサービスなどと組み合わせるならCloud9の方が親和性が高い。環境構築不要＆アップロードしなくてもブラウザに反映されるのでCloud9の方が便利かも？</li>
<br>
<li><strong>Azure(アズール)も伸びているが...</strong><br>大企業に採用されることが多い印象。AWSはアカウント乗っ取りなどセキュリティ面で不安がまだある。</li>
</ul>
DeepLのChrome拡張を入れたらテキストエリアを拡大できなくなる件

## 解決したい問題
2023/01/22現在、大人気翻訳ツール[DeepLのChrome拡張機能](https://chrome.google.com/webstore/detail/deepl-translate-reading-w/cofdbpoegempjloogbagkncekinflcnj?hl=ja)をインストールすると、テキストエリアの拡大ができなくなり、非常に不便です。

DeepLのChrome拡張機能をインストールすると、テキストエリアのリサイズ位置をDeepLアイコンが絶妙にディフェンスしてきます。
![スクリーンショット 2023-01-22 13.25.57.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/539971/c3e01b2b-8246-eaf9-3fbb-2900aaac4987.png)

## 解決していく
オプションでアイコン消せそう、消せば解決しそうですよね。
やっぱりオプションはありました。
![スクリーンショット 2023-01-22 13.28.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/539971/a3448204-5042-ba55-1a2c-90908a9b75ad.png)

おーアイコンは消えました。
ですが、テキストエリアのリサイズができません。
どうやら見えない壁があります。
![スクリーンショット 2023-01-22 13.24.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/539971/46ef174b-0d11-4e79-d642-d211c6befed8.png)

いました。
`z-index: 1999999999;`...
高すぎる見えない壁ですね...
![スクリーンショット 2023-01-22 13.27.06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/539971/03291d10-45a8-4182-4516-5f2691065dd3.png)

いろいろ解決方法があるかとは思いますが、
今回は、目には目をChrome拡張にはChrome拡張をということで、見えない壁を打ち砕くChrome拡張をサクッと作成してみようと思います。

要は`<deepl-inline-translate>`要素さんを削除するだけで良さそうですね。
親要素(`<deepl-inline-translate>`)を取ってきて、丁寧に子要素さん達を削除してあげます。
DeepLアイコンが再生成される度に削除したいので、再定義可能な`var`で変数宣言しています。

```remove.js
var elements = document.getElementsByTagName('deepl-inline-translate')
while (elements.length) {
  elements.item(0).remove()
}
```
どのタイミングでDeepL要素兄やん達を削除するかですが、
都度削除したスッキリ感を味わえるように、今回作成するChrome拡張アイコン押下で削除できるようにします。
アイコン押下で`remove.js`発火ですね。
アイコン押下で特定のjsファイルを発火させるために、`chrome.scripting`APIを使用しています。

```background.js
chrome.action.onClicked.addListener((tab) => {
   chrome.scripting.executeScript({
     target: {tabId: tab.id},
     files: ['remove.js']
   });
 });
```

後はChrome拡張を作成する上で必須の`manifest.json`を用意してあげます。
`chrome.scripting`APIを使用するためには、`manifest_version`を3以降に指定し、`scripting`パーミッションが含まれている必要があります。
ref. https://developer.chrome.com/docs/extensions/reference/scripting/#manifest

```manifest.json
{
	"name": "Remove DeepL Icon",
	"manifest_version": 3,
	"version": "0.1",
	"permissions": ["activeTab", "scripting"],
	"action": {},
	"icons": {},
	"background": {
		"service_worker": "background.js"
	}
}
```

あとは、拡張機能設定画面(chrome://extensions/)にて、「デベロッパーモード」をONにし、「パッケージ化されていない拡張機能を読み込む」ボタンから今回作成した拡張機能を読み込めばOKです。
![スクリーンショット 2023-01-22 13.49.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/539971/f17d4dcd-76f9-5978-2d63-64b339fbdd9f.png)

ソース:
https://github.com/yto-tkg/chrome_extension_remove_deepl_content

## まとめ
公開しなくてもサクッとChrome拡張を自作して読み込めるのは便利ですよね。
とはいえ、DeepLさんのアイコンはなぜそこに...
DatabricksでMETASTORE_DOES_NOT_EXISTエラーが出る際の対策

クロスアカウントのS3にアクセスする際に、IAMの設定をして接続できるはずなのに`METASTORE_DOES_NOT_EXIST`エラーが出ることがあります。

```py:Python
display(dbutils.fs.ls("s3a://ty-databricks-cross-account-bucket"))
```

![Screenshot 2023-01-22 at 13.49.08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/e97b84c5-2f14-681e-d6e8-bd938ead9081.png)

```
AnalysisException: [RequestId=ac5c871a-62d6-4f43-8799-7ab10a58da75 ErrorClass=METASTORE_DOES_NOT_EXIST] No metastore assigned for the current workspace.
```

# 発生条件

これは、以下の条件で発生します。

- Unity Catalogがセットアップされていない。
- Personal Computeの(あるいはアクセスモードが設定されている)クラスターを使用している。

Personal Computeは[こちら](https://qiita.com/taka_yayoi/items/199cc6574ab0782d5d55)で説明していますが、Unity Catalogへの接続を前提としたクラスターを作成します。クロスアカウントのS3にアクセスするなどした際、Unity Catalogのメタストアを確認しに行くのですが、これが存在しないため、このようなエラーになっています。

# 対策

Unity Catalogを[セットアップ](https://qiita.com/taka_yayoi/items/6c6f3a2e6febd9e0a451)すればいいのですが、もう一つの方法として「Unity Catalogを参照しに行かないクラスター」を作成するというものがあります。これは現時点ではレガシーとなりますが、上述のアクセスモードを設定しないクラスターを作成することになります。

1. **コンピューティングを作成**をクリックします。
![Screenshot 2023-01-22 at 13.54.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/a324ef11-7744-77a3-1e0d-1d3edf1cdcf0.png)
1. 画面上の**UIプレビュー**にマウスカーソルを移動します。トグルスイッチが表示されるので、これをオフにします。レガシーなクラスター作成画面に変更されます。
![Screenshot 2023-01-22 at 13.55.22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/86692d82-bdcd-8b72-053a-5a50ccb40fff.png)
1. **クラスターモード**を**シングルノード**などにして、クラスターを作成します。必要に応じて、インスタンスプロファイルやSpark設定を行い、S3やGlueにアクセスできるようにしておきます。
![Screenshot 2023-01-22 at 13.57.56.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/24a623fa-125b-58fa-ab7c-b46b51744694.png)

これで`METASTORE_DOES_NOT_EXIST`エラーを解消できるはずです。

### Databricks 無料トライアル

[Databricks 無料トライアル](https://databricks.com/jp/try-databricks)
npm ciと.npmを使ってGitHub Actionsを高速化する

# 概要

- Node.jsを使用しているCI/CD環境(今回はGitHub Actions)を高速化させたい
- 高速化のために `npm ci` と `.npm` をCIでキャッシュする手法を用いる

# `npm ci` とは

- `npm ci` は `package-lock.json` を参照して依存関係をインストールするコマンド
- 既に `node_modules` が存在する場合は一旦削除してからインストールが走る
- とはいえ `package.json` と `package-lock.json` のバージョン指定が食い違っている場合にはエラーを出してくれる
  - e.g. あるパッケージをバージョン `0.9.9` でインストール後に `package.json` のバージョンだけ `1.0.0` に書き換えた場合等
- 通常の `npm install` の場合、  `package.json` と `package-lock.json` の両方を見て、依存関係の解決と `node_modules` へのインストールと、場合によっては `package-lock.json` の更新も行われる
- `npm ci` を使うことで、開発時と運用時のパッケージのバージョンの差異を無くすことができる他、インストールにかかる時間もある程度短縮できる
- npmではなくYarnを利用する場合は `yarn install --immutable --immutable-cache --check-cache` で近い挙動が実現できる

# `.npm` とは

- `.npm` はnpmのパッケージのキャッシュ
- 通常はホームディレクトリ配下に設置されている
- インストール時に目当てのパッケージのキャッシュが `.npm` 配下に残っていると、ネットワークへのアクセス無しにインストールすることが可能となり、結果としてネットワークレイテンシが削減できる
- このキャッシュをCIのキャッシュに含んでやることでさらなる速度向上が期待できる
- ちなみに `node_modules` 自体をキャッシュしていても、 `npm ci` を使うと毎回削除されてしまうので意味がない
- npmではなくYarnを利用している場合は、 `~/.yarn-cache` にキャッシュが保存される

# GitHub Actionsにおける設定

- 実際には以下のような設定をしてやると良い

```diff_yaml:.github/workflows/main.yml(抜粋)
...

jobs:
  build:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout master branch
        uses: actions/checkout@v3

      - name: Use Node.js
        uses: actions/setup-node@v3
        with:
          node-version: 18.13.0

+      - name: Cache npm directory
+        uses: actions/cache@v3
+        with:
+          # CIでキャッシュするディレクトリやファイルのパス
+          path: ~/.npm
+          # キャッシュを保存・復元する際のキー
+          key: ${{ runner.os }}-npm-${{ hashFiles('**/package-lock.json') }}
+          # キーで指定したキャッシュがヒットしなかった際に代理として使用されるキー
+          restore-keys: ${{ runner.os }}-npm-

+      - name: Install node modules
+        run: npm ci

      - name: Build app
        run: npm run build

...
```
2022年現在、win10にHEWを入れてミニマイコンカーを開発する方法

# 物理的に必要なもの

- ミニマイコンカー　本体
- 単三乾電池 × 4
- プログラム書き込みケーブル（USB A-B）
- USBポート・windows10を搭載したパソコン

# HEWのダウンロードとインストール

ダウンロードURL：https://www.renesas.com/jp/ja/software-tool/cc-compiler-package-rx-family#download

**【無償評価版】HEW付き RXコンパイラ**
というのをダウンロードしてインストールしましょう。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/499476/7f7c4d10-a8be-7210-8957-c030756ae8bc.png)
画像1　HEWダウンロードページのスクリーンショット

これは罠ですよね（？）。
RXのパッケージに紛れてるんだもん。
PHPerが学ぶGo言語③ 例外処理

っす。豚野郎です。
今回は例外処理を書いていきます。

Go言語は例外処理構文(try、catch等)がありません。
その中で例外処理を実行していきます。

<font color="Red">※ 注意：内容はPHPか何かの言語を書いたことがある方向けなので、
説明を割愛している箇所は多々ありますので、ご了承ください。</font>

**go version go1.19.4 darwin/amd64**

# 1. fmt.Errorf()
```sample.go
package main

import "strconv"
import "fmt"

// fmt.Errorf()で例外情報作成
// fmt.Errorf()の戻り値の引数はerrorにする。
func Calculation(num int) (string, error) {
	if num != 1 {
		// Go言語では、エラー情報を2番目に返すことを推奨されている
		return "", fmt.Errorf("1ではありません。")
	}
	num += 1
	return "1 + 1 = " + strconv.Itoa(num), nil
}

func main() {
	fmt.Println("1を使って足し算を始めます。")
    total, e := Calculation(2)
	
	if e != nil {
		fmt.Println(e)
	} else {
		fmt.Println(total)
	}
}
```
```
$ go run sample.go
1を使って足し算を始めます。
1ではありません。
```


# 2. Goto文
```sample.go
package main

import "strconv"
import "fmt"

func Calculation(num int) (string, error) {
	if num != 1 {
		// Doneの処理を呼ぶ
		goto Done	
	}
	
	num += 1
	return "1 + 1 = " + strconv.Itoa(num), nil

	Done:
		return "", fmt.Errorf("1ではありません。")
}

func main() {
	fmt.Println("1を使って足し算を始めます。")
    total, e := Calculation(2)

	if e != nil {
		fmt.Println(e)
	} else {
		fmt.Println(total)
	}
}
```
```
$ go run sample.go
1を使って足し算を始めます。
1ではありません。
```

# 参考
ありがとうございました。

https://www.tohoho-web.com/ex/golang.html

https://tokitsubaki.com/go-exception-handling/259/#toc2
CNNについて理解する

# 目的

* アウトプットして理解する

# CNNとは

## 一言で言うと、、、

* 高次元データを次元削除して深層学習を行うことができるアーキテクチャ。

## 最初のモデル
* 人間の視覚をモデルに考案されたもの。
    * 局所受容野という性質を活かしたものともいえる。
* [このサイトがわかりやすい。](https://www.imagazine.co.jp/%E7%95%B3%E3%81%BF%E8%BE%BC%E3%81%BF%E3%83%8D%E3%83%83%E3%83%88%E3%83%AF%E3%83%BC%E3%82%AF%E3%81%AE%E3%80%8C%E5%9F%BA%E7%A4%8E%E3%81%AE%E5%9F%BA%E7%A4%8E%E3%80%8D%E3%82%92%E7%90%86%E8%A7%A3%E3%81%99/) 
* 要は、光を視神経を通じて、脳に像として認識させているということ。

## 局所受容野ってなにー？

* ニューロンが、入力データのごく一部にのみ応答するという性質のこと。
* 単純型細胞と複雑型細胞に構成されているもの。
    * 単純型細胞は、形状に反応を受ける
    * 複雑型細胞は、特定の傾きの線分が移動しても認識することができる。

* CNNでは
    * 単純型細胞が畳み込み層
    * 複雑型細胞がプーリング層　と置き換えられて利用されているよー


# では、畳み込み層とプーリング層ってなんぞや

## 畳み込み層

* 畳み込み層は畳み込み演算を行う層
* 畳み込み演算は,簡単に言うと入力層とフィルターの積和演算だよ〜
* (図で示すとわかりやすいけど、面倒くさいので略)

## プーリング層(今回は、マックスプーリング層)

* 対象領域から最大値をとる演算のこと
* 特徴として、微小な位置変化に対して、ロバスト(影響されにくい)


# まとめ

* うーん理解が深まったともいえない。
* CNNを動かして、試してみて考察すると見えてくるものがあるかもしれないと思った。
[NeosVR]7zbsonファイルの使い方


:::note info
この記事では、
主にNeosVR対応アバターとして一部で配布されている7zbsonファイルの使い方を解説します。
配布されてるアバターによってドラッグ後に表示されるパネルは若干異なりますが、基本操作は全て同じです。
:::

## 7zbsonファイルの使い方

7zbsonファイルをneos(NeosVR)の画面にドラッグ、
![スクリーンショット 2022-10-04 212705.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/cbec8910-2327-c796-e175-54567cbe32cd.jpeg)

出てきたパネルの「GetAvatar」ボタンを押し、
![20221004212906_1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/f56ed559-6393-29b1-fa59-f8daeb990847.jpeg)


後はトリガーを押して「アバターを着る」を選べば着られます。
![スクリーンショット 2022-10-04 213000.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/a6b534d8-ea06-7848-ff00-1cdc4361cf3f.jpeg)

アバターを着た状態でインベントリを開き、右上の水色のボタンを押せばアバターを保存できます。
![スクリーンショット 2023-01-22 123538.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/0d3e95de-82f8-4f7d-7c94-d2d8aa605fc4.jpeg)

保存後はこのインベントリ内からダブルクリックでアバターを呼び出して着てください。
アバターを選んで雷マークを押せば、今のアバターと入れ替えですぐに着替えることも出来ます。

**一度インベントリに保存すれば、アバターを着るたびに7zbsonファイルをドラッグする必要はありません**
![スクリーンショット 2023-01-22 130957.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/43c08263-2b05-d02d-4621-2dca37711287.jpeg)


このアバターをデフォルトにしたい場合は、保存したアバターを選択してハートマークのボタンを押せば完了。
![スクリーンショット 2023-01-22 123809.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/d558b372-5037-0069-c2aa-e8f5c2300742.jpeg)

以上です。
ツール不要でとても簡単に導入出来ます。

### エラー画面が表示された場合
<details><summary>クリックして展開</summary>

一部アバターは、ドラッグ操作後にこのようなパネルが出てくる場合があります。
![スクリーンショット 2023-01-22 124522.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/2cb5a481-51c1-7067-6d28-6ce4ed9622cc.jpeg)

これは導入時に第三者からの盗難を防ぐために設定されている機能で、
プライベートなワールドで一人で取り出した場合のみ正常にアバターを着られるように設定されています。

対応方法は下記のとおりです。

ダッシュメニューを開いて、ホームタブから新規ワールド作成を選びます。
![スクリーンショット 2023-03-20 180158.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/76f79ad5-6f59-94e5-b69f-e5b83797617a.png)

次に出てきたセッション設定で「プライベート(招待のみ)」を選んだ後
「セッション開始」を押します。
![スクリーンショット 2023-03-20 180548.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/e909fa76-f03b-8326-be2d-c1a0cf7677ce.png)


ワールドが移動するので、この中で上記の導入方法をもう一度試してください。
終わったらダッシュメニューのホームタブ右上の「セッションを閉じる」を押すことで作ったワールドを閉じられます。
今回はワールドの保存は必要はないので、保存するか尋ねられたら「変更を破棄」を選択してください。
![スクリーンショット 2023-03-20 180635.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/9f665433-dfd0-10a4-273e-0b06c51698c2.png)


</details>


## サポート
NeosVRの日本コミュニティでアバター設定や利用に関するサポート窓口を用意しています。
不明点がありましたら下記のDiscordサーバーでお尋ねください。
https://discord.com/channels/673668075718967296/1025960979709833216
PythonでのDebug方法 (もう`print()` は使わない)

tl,dr;
-
* コードのデバッグに`print()`はデメリットが多いため使わない
* 代わりに`Logging`を使う
* ベストプラクティスがありそうだが、わからない

Summary 
-
プログラムを書くときに不可避のエラー。これまでは、エラーが発生した際にはエラーメッセージを元にコードの怪しいと思われる箇所に `print('check')` などと入れることで、エラー箇所の特定を行なっていた。しかし、これはどうにもエンジニアっぽくない。そしてなんかダサい。
というわけで、脱`print()`の方法を探すと、`Logging`というデバッグ用の基本モジュールがPythonには用意されていた。
Logging HOWTO: https://docs.python.org/3/howto/logging.html

Why use logging (don't use `print()`)
-
`print()`を使うデメリット
* 効率性の問題
    * `print('checkpoint 1')`など内容をユニークにして打ち込む必要がある。怪しい箇所がすぐに特定できない場合は、大量にコード内に`print()`を入れる必要がある。かつ、挿入箇所を自分で覚えている必要がある。。。。
    * コードが長くなるほど、作業時間が増え効率性が落ちる
* 表示の問題
    * stdout(console)に表示されるため邪魔  
    * バグ修正した後に、最後に全ての`print()`を消すという作業が発生する。しかしもし追加コードを書き、バグが起こったら再度`print()`を書く、、、、以下略 
* 保存性の問題
    * `print()`しているだけなので、保存されない

`Logging`のメリット
* 上記を解決できる

How
-
基本的には公式リフェレンスに書いてある通りだが、`import logging`をした後に、表示させたい level, format, filepathなどを指定し、`print`の代わりに`Logger`クラスインスタンスを呼び出す。
ex. `logger.debug`
```python
import logging

logger = logging.getLogger(__name__)
logger.setLevel(logging.DEBUG)
f = logging.Formatter('%(asctime)s - %(levelname)s - %(name)s - %(message)s')
fh = logging.FileHandler('./log/test.log')
fh.setFormatter(f)
logger.addHandler(fh) 

    def read(self):
        logger.debug('Start of read')
        ...
```

Next Action
-
**Start**
* 今後は`print()`ではなく、`Logging`を使ってdebugしていく

**Stop**
* コードがエラーを起こした時に、脳死的に`print()`を使うのをやめる

**homework**
* いま学んでいる`Try - except`や`unittest`とうまく組み合わせる方法を知りたい。
Voltaのインストール

voltaはnodeの管理ツールです。

https://docs.volta.sh/guide/

こちらの記事を読んでvoltaすごいと思ったので自分も入れてみました。

https://zenn.dev/aiueda/articles/7dcecaa05d4f24

# 何が良いの？
1. 迅速なセットアップ
    1. projectごとに設定されているnodeやnpmの環境に自動で切り替わる。
    2. Rustで作られており高速
2. OSに依存しない
    1. MacやWindowsどちらを使っていても同様の環境を構築できる

# 手順
公式に沿ってやればすぐできました。
https://docs.volta.sh/guide/getting-started

```bash
# macの場合
$ curl https://get.volta.sh | bash
$ volta install node # ltsが入る
# volta install node@latest

# 確認
$ node -v 
#> v○○.△△.□□
```

:::note warn
既に別のnode管理ツールを使っていた場合は削除してからのほうが良い
- nodebrewを使って管理していた場合
    - [https://qiita.com/mame_daifuku/items/373daf5f49ee585ea498](https://qiita.com/mame_daifuku/items/373daf5f49ee585ea498)
- nodeenvを使って管理していた場合
    - [https://zenn.dev/kubio/articles/ba751debd01f88](https://zenn.dev/kubio/articles/ba751debd01f88)
:::




# Tips
○プロジェクトで環境を指定する時
```bash
$ cd <project>
$ volta pin node
$ volta pin npm

#> package.jsonにvoltaの情報が書き込まれます。
```

○pnpmもinstallできました！(公式には載ってなかった？)
```bash
$ volta install pnpm
```
pythonからMatlabを動かす -Windows編-

# はじめに
pythonからMatlabでつくった関数を読み込んで動かす方法を記述。
もうすでに[記事にされている方](https://qiita.com/hinata/items/c4cfb7993cc98373b642)がいるのですがWindows ver ということでご容赦願いたい。

# 想定する読者
- Matlab関数で書かれた資産をpythonで読み出して使いたい人
- WindowsOSの人
- pythonインストールは自力でできる人（pipなど）

今回は、matlabで用意した関数をoptunaと呼ばれるパラメータ探索手法を用いて、Matlabで定義した関数の最適値をpythonで探索するまでの一連の手順を記載します。

# 動作環境
Matlab R2022b
Windows 10
python 3.10 インストール済み想定
pip install optuna も実施済み

# 実施手順
- python用Matlab engine をpython上にインストールする。

```python
python -m pip install matlabengine
```

- Matlab用関数を準備
簡単な2次関数の値を返す関数です。
```matlab
function [c] = function_matlab(a,b)
 c = (a-3)^2 + (b-0.5)^2;
end
```

- test用pythonを準備
ここでは、先程作成したfunction_matlab 関数をmatlab.engineを通して呼び出して、
その値を最小化するXとYを探索します。
xは-10から10の連続値、y はリストの中の値で最適値を探します。

```python
import optuna
import matlab.engine
eng = matlab.engine.start_matlab()

def objective(trial):
    x = trial.suggest_float('x', -10, 10)
    y = trial.suggest_categorical('y', [-1, 0 , 0.3 , 0.6, 2])
    c = eng.function_matlab(x,y)
    
    return c

study = optuna.create_study()

study.optimize(objective, n_trials=100)
print(study.best_params)
````

- 上記pythonコードを実行します。その際にMatlab関数と、pythonソフトは同じフォルダに入れておいてください。

# 実行結果
100回の試行で　x=2.99,  y=0.3 がベストと探索できてます。
関数から考えて、x=3, y=0.5が関数の最小値なので、無事探索できてます。
またMatlab関数をpythonで読み出して　最適化できています。


``` python
[I 2023-01-22 12:10:36,995] Trial 98 finished with value: 1.3919151142684436 and parameters: {'x': 1.8372811542473204, 'y': 0.3}. Best is trial 96 with value: 0.04007151564978928.
[I 2023-01-22 12:10:37,018] Trial 99 finished with value: 0.45619130467454294 and parameters: {'x': 2.3548710945287423, 'y': 0.3}. Best is trial 96 with value: 0.04007151564978928.
{'x': 2.9915433073965483, 'y': 0.3}
```

# 終わりに
Matlabのツールボックスが充実してきているので、そのうちこんな面倒な使い方はしなくなるのでしょうが、自身の記憶保持も兼ねてメモを残しておきます。
Laravel9にJetstream入れた話

Laravel9にJetstream入れた話

前の記事

https://qiita.com/nekooosaka/items/3d111eb1228f44b723b5

の続きです

.envファイルを編集します．
もしかして，.envファイルって＝の前後にスペース入れない方がいいのかな？

```.env
DB_CONNECTION=mysql
DB_HOST=my_db  //dbはdocker-compose.ymlにあるmysqlのコンテナ名です
DB_PORT=3306
DB_DATABASE=my_database  //dbのデータベース名
DB_USERNAME=mydbuser      //dbのユーザー名
DB_PASSWORD=mydbpass  //dbのパスワード
```

#### ちょっと記憶が曖昧．
Backendを入れてみたのでしが，Jetstreamとちょっとうまく使いこなせる自身が無かったのでアンインストールしたりでファイルがぐちゃぐちゃになってる感あり．

### Jetstream

Jetstreamをインストールします．

参考にしたサイト
https://biz.addisteria.com/jetstream_livewire_install/

**Docke内のターミナルで作業です．**

まずjetstreamをひっぱってきます．

`composer require laravel/jetstream`

Jetstreamのlivewireのチーム版をインストールします．

`php artisan jetstream:install livewire --teams`

次にnpmをインストールします．

`npm install`

エラーが出たら

`apt-get install -y npm`

して，

`npm install`

をします．


### テーブル作成
テーブルを作成します．

`php artisan migrate`

Web画面をリロードするとログイン機能がつきます．

### このあたりでいっぱいエラー出たよ

なので，npmのバージョン変更をするといいらしい（参考サイト）

https://biz.addisteria.com/jetstream_livewire_install/

Dockerfileにこの件を反映した記憶が，，

### Registerをクリックしたらロゴがめちゃくちゃ大きい

これを参考にしました．

https://qiita.com/hitotch/items/aa319c49d625c2a9b65e

### 日本語化
日本語化は以下を参考にしました．

https://zenn.dev/kishimoto/articles/fcd745ccbf41a8
Googleプロジェクト管理：ストーリーテリング

# はじめに

わたしが [Google プロジェクト管理:プロフェッショナル認定証で得られた素晴らしい体験][google]を、要点をまとめ小さく分割して、わかりやすく簡潔に紹介していきます。

興味があれば、ぜひ ***"Google プロジェクト管理:プロフェッショナル認定証"*** を受講してみてください。

[google]: https://qiita.com/mapami/items/317ae776a2268fd54c8f

https://jp.coursera.org/professional-certificates/google-project-management

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/dc97f9d2-8c30-5310-a190-3fb484c9c091.png" width="800">

# ストーリーテリング

プロジェクトデータを収集・整理して、組織内の人にプレゼンテーションする方法を紹介します。

***<font color="MediumVioletRed">『プレゼンテーションとは、プロジェクトのストーリーを語ること』</font>***

ストーリーテリングは、データに命を吹き込む方法であり、組織内の関係者にプロジェクトについて伝えるのに有効な方法です。

データを使って素晴らしいストーリーを語るために、ストーリーが完全で正確、かつ説得力のあるものになるよう、いくつかのベストプラクティスを紹介します。

ストーリーテリングには6つの主要なステップがあります。

1. オーディエンスを定義する
2. データを収集する
3. データをフィルタリングし、分析する
4. 視覚的な表現を選択する
5. ストーリーを形成する
6. フィードバックを集める

## <font color="MediumBlue">1.オーディエンスを定義する</font>

プレゼンする相手を知ることが重要です。

- プロジェクトのスポンサーや経営者に向けて発表するのでしょうか？
- チームメンバーに対してでしょうか？

オーディエンスを定義し、彼らにとって何が最も重要なのかを調べます。

まず、次のような質問を自分に投げかけてみましょう。

- **オーディエンスはこのプロジェクトについて何を知りたがっているのか？**
- **最も緊急な懸念事項は何か？**
- **ストーリーやプロジェクトの結果に影響を与える重要なデータポイントは何か？**

こうすることで、どのようなストーリーを語りたいのか、そのためにどのようなデータを使用すべきなのかを知ることができます。

:::note info
例えば、数年前、私はGoogle Mapsのプロジェクトに関わっていました。レストラン、ホテル、ガソリンスタンドなど、世界中のあらゆるビジネスにラベルを付けることが目的でした。レストラン、ホテル、ガソリンスタンドなど、世界中には膨大な数のビジネスがありますが、私は小さなエンジニアのチームしか持っていませんでした。このプロジェクトでは、GoogleマップとGoogle検索の副社長を対象に、ストーリーテリングを行いました。なぜなら、私たちは、GoogleマップアプリとGoogle検索を通じて、ユーザーが企業を見つけ、つながることを支援していたからです。
:::

## <font color="MediumBlue">2.データを収集する</font>

次のステップは、答えたい質問につながるデータを探すことです。

信頼できるリソースから、あなたが主張したいことを裏付けるデータを探し始める必要があります。プロジェクト計画書や作業管理ソフトウェアなどの文書にある関連するプロジェクトリソースを活用し、主要なデータポイントをダウンロードして分析します。

:::note info
私のGoogle Mapsプロジェクトでは、次のような問いに答えようとしていました。
- まず、どこに注目すべきなのか？

そこで、この質問に適したデータを見つけるために、社内のデータベースにある多くのビジネスと、ユーザーがどのようなビジネスを検索しているかという利用可能な情報に目を向けました。
:::

## <font color="MediumBlue">3.データをフィルタリングし、分析する</font>

データのフィルタリングと分析データを収集したら**、**その**信頼性を検証し、情報をフィルタリング**する必要があります。

:::note info
私のGoogle Mapプロジェクトでは、検索クエリを使用して、ユーザーが最も頻繁に検索するビジネスの種類を特定しました。他にもガソリンスタンドや美術館などがありましたが、地域別の検索トラフィックに占める割合ははるかに低いものでした。
:::

## <font color="MediumBlue">4.視覚的な表現を選択する</font>

ビジュアル化は、提示する情報を覚えてもらうための優れた方法であり、ストーリーテリングの重要な要素でもあります。

- ダッシュボード
- チャート
- インフォグラフィックス
- マッピング

の使用など、データをさまざまな方法で使用してストーリーを伝えることができます。

:::note info
私のGoogleマッププロジェクトでは、ストーリーを伝えるために円グラフを使うことにしました。
:::

## <font color="MediumBlue">5.ストーリーを形成する</font>

データを分析し、どのように可視化したいかが決まったら、次はそれを1つのまとまった物語にする番です。何を達成したいのか、何を主張したいのか、疑問や質問に答えたいのか、じっくり考えてみましょう。

:::note info
Google Mapプロジェクトでは、円グラフを使って、地域別の検索クエリのほとんどが、比較的少数の企業によってカバーされていることを示しました。そこで私たちは、そのデータに関するストーリーを構築しました。私たちは、いくつかの主要な市場において、この一連のカテゴリの背後にあるデータの改善に取り組むことに、副社長の同意を求めました。カテゴリーデータを改善すれば、地域別検索の50%以上の検索結果を改善することに成功することを説明する必要があったのです。
:::


## <font color="MediumBlue">6.フィードバックを集める</font>

面接の前に友人に練習を頼むのと同じように、プレゼンの前にも必ず試行錯誤をしたいものです。プロジェクトに関係のない人からフィードバックをもらってみてください。

- 面白かったかどうか
- 筋が通っているか
- どんな疑問があったのか

彼らのフィードバックは、あなたのストーリーの不明瞭な部分や記憶に残らない部分を特定するのに役立ち、最終的な調整の機会を与えてくれるでしょう。
【流出解析】シリーズ　第11回　表面流モデル【定常降雨：前編】

# 移転のお知らせ

こちらの記事は下記のサイトに移転しました。

> [NNテックブログ](https://nnhiroba.xsrv.jp/nnTechBlog/Article/Article?ID=43)
オブジェクト指向は現実と似て非なり~オブジェクト指向でなぜつくるのか一部要約〜

## はじめに
**「オブジェクト指向」** について、なんとなくはわかっていたものの、何となくのままだなと。
今回はこちらの本を読んだアウトプットをできればと思います。※要約のような、一部個人の解釈も含まれます

https://amzn.asia/d/2O347SF



## よくある現実世界のお話
オブジェクト指向について学んでいくと、現実世界での例えってよくありません？
本書の中でも↓が1例として出ていました。
> 動物がスーパークラスで、哺乳類や魚類がサブクラス。卵を生みミルクで子どもを育てるカモノハシは、爬虫類と哺乳類を多重継承している。


またオブジェクト指向を調べるとよく出てくるのが車の例えだと思います。

>車の共通部品：ハンドル、ブレーキ、アクセル、内装、外装
A車には共通部品使い、個別部品として特別な内装を追加したり
B車には共通部品使い、個別部品としてパトランプを追加したり（パトカーやん）


といったケースですね。

これを見るとなるほど、、とも思いつつ、
プログラミングの世界とどのように紐づくのかが個人的にはあまり見えず、、といった状態でした。

本書の中では、**現実世界とは似て非なるもの**だと記載されていました。
なぜなら、現実世界とは異なる部分が多々あるからです。

例えば、オブジェクト指向では最初にクラスを定義し、そこからインスタンスを作りますが、
現実世界では動物クラスから犬が作られるわけではないです。
個人的には最初の取っ掛かりとして例えから入って理解するというのは良さそうですが、
プログラミングとの接続となると難しい印象を持ちました。

本書の中でも、現実世界のものはあくまで例えであり、
オブジェクト指向はプログラミングのための仕組みとして割り切って理解べきとされていました。


## オブジェクト指向の三大要素
では実際のオブジェクト指向にについて。
オブジェクト指向の三大要素は **「クラス」「ポリモーフィズム」「継承」** です。
それぞれまとめていきます。

### クラス
クラスは **「①まとめて、②隠して、③たくさん作る」** 仕組みです。

#### ①まとめる
ここでは変数とメソッドをまとめることを指しています。
変数とメソッドをまとめたところで、、となるかもしれないですが、
部屋を整理整頓するときに、洋服、文房具、書籍、、と箱を分けた方がわかりやすいですよね。（ここでも現実世界の例え）

まとめることのメリットとしては2つあります。
・全体の部品の数を減らせること
まとめることで、同じものをいくつも作ってしまうといったことは減らせます。
こちらは大きなアプリケーションになればなるほど効果を実感しやすそうです。

・命名が楽になる
クラスがないと、全てのメソッドに別々の名前が必要になりますが
クラスに格納することで、クラス内で重複しなければOKです。
これもメソッド数が増えれば増えるほど重複しないようにしなければならず、クラスがあることの効能は大きそうです。


#### ②隠す
こちらはクラスに定義した変数とメソッドを他のクラスから呼び出せないようにするということです。

他のクラスから呼び出せない（アクセスできない）ことによって、影響範囲を限定することができます。
それによっって例えば変数に予期しない値が入って不具合が起こったととしても、該当のクラスの中にあるメソッドだけを確認すればよかったりします。
逆にどこからでもアクセスできてしまうと、どこから参照されているか分からない＝影響範囲が分からないといったことになります。

逆に他のクラスからｄめおアクセスできるようにしておきたいというケースもあるかと思いますが、
クラスでは、時々のケースに応じてpublic、privateで明示的に隠すかどうかを決めることができます。


#### ③たくさん作る
クラスからたくさんインスタンスを作ることができる、といった意味です。
クラスで一旦定義をするとインスタンスをいくつでも作成ができ、
かつクラス内のロジックはシンプルにすることができます（文字での説明が難しい、、）


以上の **「①まとめて、②隠して、③たくさん作る」** が三大要素の①クラスの特徴です。



### ポリモーフィズム
続いて、2つ目のポリモーフィズムについて。
**「共通メインルーチンを作るための仕組み」** とここでは記載されています。
そもそもメインルーチンとはなんぞや？はこちらで該当が書かれているので一応リンク貼っておきます。

https://wa3.i-3-i.info/word1501.html

**呼び出される側が増えても、呼び出す側を修正する必要がない** 、というのが大きな特徴かと思います。

（ちょっとここは書籍だけでは自分の理解が不足しているので、また追記したい。です）

### 継承
最後3つ目の継承について
一言で言うと **「クラスの共通部分を別クラスにまとめる仕組み」** です
共通部分をクラスにまとめられるので、コードの重複を防ぐことができます。

```JAVA
public class XXX extends YYYY{
}
```

YYYYに共通部分を記載することで同じ記述はしなくてすむということですね。





#### 終わりに

以上、ざっと特徴を言語化してみました。
個人的には現実世界の整理整頓術に似ているのかなという印象です。
オブジェクト指向とは？をなんとなくは理解したかなと、、いや、まだまだですね。
特にポリモーフィズムの理解がまだまだ（難しかった、、）
一旦は手を動かしながら理解していきたいです。
手を動かして、本読み直して理解深めていけたらと思います。
RHEL8へのsambaインストール～共有設定

# samba for RHEL8

## install
```
# dnf install samba samba-client samba-common
```
## サービス起動設定
```
# systemctl start smb
# systemctl enable smb
# systemctl status smb
```

## firewall設定
```
$ firewall-cmd --permanent --add-service=samba
$ firewall-cmd --reload
```

## 共有用ディレクトリ作成と設定
```
# mkdir -p /srv/samba/anonymous
# chmod -R 0777 /srv/samba/anonymous
# chown -R nobody:nobody /srv/samba/anonymous
chconユーティリティを使用して、作成したsamba共有ディレクトリのSELinuxセキュリティコンテキスト
# chcon -t samba_share_t /srv/samba/anonymous
```

## smb設定（匿名共有のセクションを追加）
```

[global]
        workgroup = WORKGROUP
        netbios name = rhel
        security = user
...
[Anonymous]
        comment = Anonymous File Server Share
        path = /srv/samba/anonymous
        browsable = yes
        writable = yes
        guest ok = yes
        read only = no
        force user = nobody
```

## samba構成チェックとサービス再起動
```
# testparm
# systemctl restart smb
```

## samba接続ユーザ設定(anonymousできない場合)
```
# pdbedit -a ユーザー名（すでに作成してあるユーザを指定：例）masa）
```
【2024年卒】自己分析に使えるツールまとめ

# 概要
2023年が始まり、そろそろ本選考の準備が本格化する時期だと思います。

しかし就活をまだ始めたばかりの人もいるはず。
そこで本記事では、就活で最も重要なフェーズの一つである「**自己分析**」を進めるうえで参考にしたツール・イベントをまとめています。

:::note warn
自分が就活で活用したツール等を紹介していますが、あくまで個人の意見である事を予めご了承ください。
:::

## そもそも自己分析とは

就活をしている方なら一度は耳にする「自己分析」というワードですが、具体的にはどんな事をするのでしょうか？

就職情報サイトのマイナビは自己分析を以下のように定義しています。

>就活における自己分析とは、自分の特徴や長所・短所、価値観を把握・分析し、自分の『強み』を見いだすことです。

同様に、自己分析の目的を以下のように紹介しています。

>【1】将来の目標やキャリアプランを見つけるため
>【2】自分自身の価値観を明確にするため
>【3】長所や短所などの特徴を見つけるため
>【4】自己PR・志望動機を具体的にするため

私はさらに「**企業の取捨選択ができ、就活によって時間・メンタルが食いつぶされることを防ぐ事**」が自己分析の目的の一つだと考えています。
昨今コロナ禍の影響により選考の多くがオンラインに移行しました。確かに移動もせず様々な企業を見ることができるので選択肢が増えたのは事実ですが、一方で選択肢が多すぎて片っ端から参加していると**時間と体力とメンタル**が持っていかれます（実体験）。
そのため、自己分析を最初に行い、自分に合わない企業の選考を切り捨てる必要があるのです。
また自己分析は就活だけでなく、社会人になってもキャリアを考えるための重要な作業になります。就活だけだからと何となくで終わらせず、今後の予行演習だと思って取り組むと良いかもしれません。

# 自己分析で使えるツール・イベント

## モチベーショングラフ
モチベーショングラフとは、自分の過去を**曲線グラフ**を用いて振り返り、人生のモチベーションが高い時と低い時を可視化する方法です。これにより、自分がやる気をもって出来る仕事や働き方を考えることができます。

**メリット**
* 曲線グラフを書くことで過去を可視化できる
* やりがいを持てる仕事や働き方の傾向を掴める
* 自分の短所も同時に振り返ることができる

**デメリット**
* 細かい振り返りをするのが難しい
* デジタルツール上で実施するのが少し面倒


**テンプレートを提供しているサイト**
https://offerbox.jp/columns/20436.html

## マインドマップ
マインドマップとは、中心となる概念から**様々なアイディアや情報を分岐**させていく手法です。これにより、自分が過去何を考え決定したか、自分史を簡単にまとめる事が可能です。また自己分析だけでなく、企業分析にも用いることが可能です。

**メリット**
* 連想ゲームのように脳内を整理可能なので、悩みにくい
* 様々な内容について作成可能
* 大量の情報をまとめる事が可能

**デメリット**
* 情報量が増えると、視認性が悪くなる
* 文章としてまとめるのは難しい

**おすすめのマインドマップツール**
* [MindNode](https://www.mindnode.com/)…デザインがおしゃれかつ使いやすい。Windows版はなく、Mac版とiPhoneアプリが提供されている。
* [GitMind](https://gitmind.com/jp/)…PC、スマホなどデバイス問わず使用可能。シンプルな使い心地。

# 診断ツール
診断ツールとは、複数の質問に回答し、自分が属する性格や傾向にが示されるツールです。診断ツールは占いだけでなく、自己分析をする取っ掛かりとしても有用です。

**メリット**
* 所属から思考傾向や長所短所を知ることが可能
* 手軽に自己分析を行うことが可能

**デメリット**
* あくまで一般的にはどうかという点しかわからない
* 診断だけでは自己分析不足
* 鵜呑みにするのは危険

**おすすめの診断ツール**
* [16TEST](https://16test.uranaino.net/)…16種類の性格に分類される性格診断ツール。Webだけでなく、アプリ版もある。
    * [16Personalities](https://www.16personalities.com/)…16TESTと同様16種類の性格に分類する。英語だが、無料で詳細な結果を出してくれる。
* [VIA-IS](https://www.viacharacter.org/)…VIA研究所が提供するストレングスファインダーツール。全部で２４種類の強みに分類されており、そのうちトップ５が「自分を特徴づける強み」になるとのこと。無料で受けられるが、英語。
* [エニアグラム診断](https://www.enneagram.ne.jp/about/diagnosis)…9つの性格に分類される診断ツール。エニアグラムという幾何学図形から今後のポジティブ・ネガティブな成長についても推測可能。

## 企業インターンシップ
企業のインターンシップの中には、企業説明だけでなく、自己分析や就活について相談・考える場を設けているものもあります。自分の興味がある企業でそのようなインターンシップが開催されていれば、積極的に参加してみましょう。

**メリット**
* 企業の採用側が求めている人物像を知ることができる
* 企業分析と自己分析を同時にできる

**デメリット**
* 興味のない企業を受けすぎると、本命に割く時間が減る
* 自己分析について事細かにサポートしてくれるわけではない

**おすすめ企業インターンシップ**
* [ライブレボリューション](https://job.mynavi.jp/24/pc/search/corp75729/outline.html)…自己分析・企業分析など就活について、非常に手厚い説明がある。ダウンロード版の資料をもらえたりする。
:::note warn
2023年1月時点では終了してしまっているようです。
:::

## その他のツール
* [Scrapbox](https://scrapbox.io/product)…デジタルノートツール。とにかく書きなぐりたい方向け。企業分析もできる。**超おすすめツール。**
* [Notion](https://www.notion.so/ja-jp)…タスク管理からメモまで一元管理可能な多機能ツール。就活用のテンプレートも提供されているなど、とにかくカスタマイズ性が高い。
* 友人や家族…ツールではありませんが、一人で実施することが難しければ、人に頼るのも手です。自分がどういう人間と思われているかを知ることも大事な自己分析になります。

# まとめ
自己分析は己との戦いとなり、つらくなる場面もあるかもしれません。しかしこのフェーズを蔑ろにすると、後々強烈なしっぺ返しを食らう可能性があるため、時間をかけて実施するのがお勧めです（戒め）。

この記事が、自己分析を進める上で役立つことを願っています。

# 参考サイト
https://shinsotsu.mynavi-agent.jp/knowhow/article/what-is-self-analysis.html
ABC286回答メモ

0.はじめに
　Aがいきなりめんどい感じの問題で、これは・・・と思っていたら
　C、Dも難問で24時から仕事(在宅)ということもあり
　早々に終了してしまいました。


1.A - Range Swap
　　面倒なだけで難しくはなかったのですが、Aにしては30行もかかってしまいました。

　考え方
　　１）リストAを頭から見ていき(添え字i)、iがP-1の時、A[i]とA[R-1]と入れ替えてフラグを立ててカウントに1プラス。
　　２）フラグが立っていたら、A[i]とA[R+カウント]と入れ替えてカウントに1プラス。
　　　　→i＝Q-1だったらフラグOFF
　　
　　と最初しましたが、P=Qの時うまくいかなかったので、１）の処理の時P=Qだったらフラグを立てないようにしてAC

　pythonの解答例はめちゃくちゃ短かったですが・・・。

　https://atcoder.jp/contests/abc286/submissions/38200374

2.B - Cat
　　Aより簡単じゃないの？？と謎に思いつつ回答

　考え方
　　Sを頭から回答文字列に転記していき、転記した文字が”n”かつ次の文字が"a"だったら
　　"y"を出力する。

　で、ACでした。

　https://atcoder.jp/contests/abc286/submissions/38202393

3.C - Rotate and Palindrome
　　愚直に計算したら、TLEになるだろうなーと思い、諦めてしまいましたが
　解説を見たら愚直でも間に合うようなので、試したら意外と何とかなりました。

　　考え方
　　　1)最大で、Sの半分に対してB円の操作を行えば、回文ができるのでB*(N//2)を回答ansに保持
　　　2)文字列Sについて、先頭からと末尾からを比較して、Bの操作が何回必要かをチェックし、
　　　　Aの操作をしなかったときに必要な金額を求め、ansにmin数をセット
　　　3)Aの操作を1回した場合のチェックを行いansにmin数をセット・・・・→N回まで繰り返す

　https://atcoder.jp/contests/abc286/submissions/38239580


以上
[Rails7][Heroku] Active Storage や ActionText で画像が表示されない問題を解決する

# はじめに
`Rails7` で構築したアプリケーションを　`Heroku` にデプロイしたが画像が表示されない問題を解決していきます。
`Active Storage`を使用していることを前提としています。
以下、確認・修正すべきことを書いていきます。

# 画像をアップロードしておくストレージの設定
開発環境ではローカルストレージに保存されますが、
本番環境（今回の記事では`Heroku`）では画像を保存するストレージを設定する必要があります。
これは、ググればたくさん情報が出てきます。
`AWS`の`S3`を使用する構成が簡単でしょう。
本記事では`AWS`の`S3`を使用していきます。

https://qiita.com/hmmrjn/items/479c9e9ce82771f1b6d7


# `AWS`の`S3`のバケットに`CORS`の設定を追加
`AMAZON S3` > `バケット` > `sample buket name`
↑ご自身で設定したバケットを開いてください。

「アクセス許可」というタブを選択してください。
![スクリーンショット 2023-01-22 11.25.58.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/916052/019a1215-24db-9d60-7323-2066ba90cafe.png)

スクロールしていくと
`Cross-Origin Resource Sharing (CORS)`の設定ができる部分が表示されます。
![スクリーンショット 2023-01-22 11.27.13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/916052/cbb876f5-1395-8b71-29d6-a94d2fa4cebd.png)

「編集」ボタンを押下してください。
`Json`形式で、許可する`CORS`の設定を記述します。
```json
[
    {
        "AllowedHeaders": [
            "*"
        ],
        "AllowedMethods": [
            "GET",
            "PUT",
            "POST"
        ],
        "AllowedOrigins": [
            "https://www.sample.com"
        ],
        "ExposeHeaders": []
    }
]
```
上記のCORS 設定は、任意のオリジン (*) からのすべてのヘッダー、GET、PUT、POSTメソッドによるリソースへのアクセスを許可しています。

この構成は非常に寛容であるため、必要に応じて設定を変更してください。

`AllowedOrigins` の部分で、ご自身のアプリケーションのドメインを指定しましょう。

`CORS` の設定を記述したら、保存してください。
設定が反映されるまで数分かかることがあるので、待ちましょう。


# `heroku-buildpack-vips` の設定
この設定は`Rails7` から必要になったようです。（まちがっていたらすみません）

https://github.com/brandoncc/heroku-buildpack-vips

↑を`Heroku` に追加していきます。

まずは下記のコマンドを実行します。
（アプリケーションのルートディレクトリで実行）
```bash
heroku buildpacks:add --index 1 https://github.com/heroku/heroku-buildpack-apt
```

次に、`Aptfile` を作成します。
（アプリケーションのルートディレクトリで実行）
```bash
touch Aptfile
```

`Aptfile`を開いて、以下をコピペしましょう。
```
libglib2.0-0
libglib2.0-dev
libpoppler-glib8
```

最後に、以下を実行します。
```bash
heroku buildpacks:add --index 2 https://github.com/brandoncc/heroku-buildpack-vips
```
以下のような結果が返ってきます。
```
Buildpack added. Next release on amazing-earthfest will use:
  1. heroku-community/apt
  2. https://github.com/brandoncc/heroku-buildpack-vips
  3. heroku/ruby
```

ここまでできたら、変更を反省して`Heroku`にデプロイしてください。 
```
git push heroku main 
```

# さいごに
`Rails7`の情報がまだまだ少ないために、設定に手間取ることが多いですね。。。
いろいろな情報が錯綜していますが、自分が使用している環境とマッチしているか確認することが大事ですね。
`Rails6`で動作しても`Rails7`だと動作しないことはよくありますので。
ASCIIコードをおぼえずにC++の大文字小文字変換





https://scrapbox.io/rustacean/C++%E3%81%AE%E5%A4%A7%E6%96%87%E5%AD%97_%E2%87%94_%E5%B0%8F%E6%96%87%E5%AD%97%E5%A4%89%E6%8F%9B


https://webkaru.net/clang/conversion-string-lower-to-upper-case/

上の記事の様にtolower()などを使わずに、大文字、小文字の変換をするときはASCIIコードを小文字に減算して大文字に変換、大文字を加算して小文字に変換するというやり方を多く見かけます。
その場合、大文字を減算、小文字を加算しないようにASCIIコードで変換する範囲を指定します
```C++.C++
//https://webkaru.net/clang/conversion-string-lower-to-upper-case/より引用
   /* アルファベットの小文字なら変換 */


    if(str[i]>=97&&str[i]<=122)
      str[i]=str[i]-32;
```


でも文字のことを考えているときに数字のことを考えるのは面倒くさいので小文字の場合は小文字を引いて大文字を足す、大文字の場合は大文字を引いて小文字を足す、という風にしました。


小文字
```C++:qiita.C++


  /* アルファベットの小文字なら変換 */


    if('a'<=str[i]&&str[i]<='z')
      str[i]=char(str[i]-'a'+'A'); //char()で括らないと数字として表示される
//('a'-'a'==0 → 0+'A'=='A'),('b'-'a'==1 → 1+'A'=='B')....
//('z'-'a'==25 → 25+'A'=='Z')
```



大文字

```C++:qiita.C++


  /* アルファベットの大文字なら変換 */


    if('A'<=str[i]&&str[i]<='Z')
      str[i]=char(str[i]-'A'+'a'); //char()で括らないと数字として表示される
    //('A'-'A'==0 → 0+'a'=='a'),('B'-'A'==1 → 1+'a'=='b')....
    //('Z'-'A'==25 → 25+'A'=='Z')
```


(-'a'+'A')*(1)で小文字変換

(-'a'+'A')*(-1)で大文字変換

とできるなら応用ができそう
NPSPのパッケージをインストールできない

[NPSP のまとめに戻る](https://qiita.com/Keiji_otsubo/items/41e27c51ed61deb00d44)

よく見かける

# We could not find the Nonprofit Success Pack package installed in your org. This means that your installation of NPSP was not completed successfully. Make sure you have correctly installed NPSP using the NPSP installer. 

+ [Nonprofit Success Pack](https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000MhnSK)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/d1b9a241-dedb-b8e9-c735-f0b6c24fd7e2.png)

新しいプレイグランドを使ったようです。

+ [【未解決】Trailhead Playground Error: Nonprofit Success Pack](https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000LJOgX)

+ [【未解決】The flow component on the opportunity page doesn’t appear to be configured properly. Check your settings against the instructions and click Verify again.](https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000JfpFE)

+ [【未解決】App -unable to delete custom App, profiles are this custom app as default Action- component is in use by another component in your organization. ](https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000NEFcQSAX)

+ [[【未解決】We couldn’t find the test opportunity record in your Trailhead Playground. Check your work against the instructions and try again in the following Trailhead module.](https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000O6e0f)

+ [【未解決】Hello I am Facing an issue to complete challenge unable Install Nonprofit Success Pack (NPSP) into a Trailhead Playground](https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000PfBq6)

+ [I am having trouble installing NPSP on my Trailhead Playground Org](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V000075uFvm)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/57abb9e5-5189-153c-9119-01917afa04f0.png)

:::note
Try your new playground.
:::


# Oops! It looks like you don’t have permissions to run an installation on this org.

+ [Not able to install NPSP](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V000076Bfmv)

:::note
Please check this article.

https://trailhead.salesforce.com/trailblazer-community/feed/0D54S00000K0z4MSAR
:::

# 「Nonprofit Success Pack Health and Optimization」モジュールに NPSP のインストール手順がありません

+ [NPSP installation step missing in "Nonprofit Success Pack Health and Optimization" module](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V000076Bgxm)

:::note
You can follow these instructions after installing NPSP.
Install it in your playground first.

Install Nonprofit Success Pack (NPSP) into a Trailhead Playground
https://trailhead.salesforce.com/content/learn/projects/install-nonprofit-success-pack-into-a-trailhead-playground?trail_id=nonprofit_fundraising
:::
[C++] 配列でもvectorでも使える汎用print関数



# コード
```c++:実装
template<typename iterator>
void print(iterator begin, iterator end) {
    for (iterator p = begin; p < end; p++) cout << *p << " ";
    cout << endl;
}
```

## 使い方
```c++:使い方1: vector
vector<int> vec;
// ...
print(vec.begin(), vec.end());
```
```c++:使い方2: 配列
int arr[N];
// ...
print(arr, arr+N);
```

# 実行結果

```c++:テストコード
int main() {
    int array[100];
    for (int i=0; i<100; i++) array[i] = i;
    print(array, array+100);
}
```

```:実行結果
0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99
```

## 応用
イテレータを渡すので、配列なら例えば `array+10`とかをbeginに指定すると 10番目の要素からprintできる。
endの指定についても同様。
```c++
int main() {
    int array[100];
    for (int i=0; i<100; i++) array[i] = i;
    print(array+10, array+80);
}
```
```:実行結果
10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 
```


# 参考
https://qiita.com/yokoto/items/5672ff20b63815728d90
https://qiita.com/mgmk2/items/6f4b78ef3a78c8c928f2