OmniAICreator/Qiita-1.07M huggingface dataset:
Visual Studio Code(VSCode)でキーボードによる選択を行えるようにする

# Visual Studio Codeでの選択キー問題
AtomやGolandなどの多くのエディターでは、`Ctrl + Shift + F` などで文字を選択状態にすることができます。
こういうやつです。
![スクリーンショット 2019-04-22 0.23.50.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154121/51c5ce6e-b2b1-6778-82d4-91e1b989edf1.png)

通常だと下記のようなキーバインドがよく使われますよね。

* `Ctrl + Shift + F` : カーソルから右の1文字を選択
* `Ctrl + Shift + B` : カーソルから左の1文字を選択
* `Ctrl + Shift + N` : 次の行の同じカーソル位置までを選択
* `Ctrl + Shift + P` : 前の行の同じカーソル位置までを選択
* `Ctrl + Shift + E` : カーソル位置から行末までを選択
* `Ctrl + Shift + E` : カーソル位置から行頭までを選択

しかし、Visual Studio Codeでは、上記のキーバインドが使えません。
これらを使えるようにするには、`keybindings.json`を編集しましょう。

# keybindings.jsonを編集する
## 開き方
Code > 基本設定 > キーボードショートカット
を開きます。
僕はメニューを日本語化させてますが、デフォルトの状態の場合も基本的にメニュー階層は同じかと思います。

そうすると、キーボードショートカットの画面が開くので、右上の`{}`をクリック。
![スクリーンショット 2019-04-22 0.30.29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154121/ac34c8e8-2bb5-a6d5-9306-690c09c95be2.png)

これで、`keybindings.json`が開きます。

## 記述内容
```keybindings.json
[
    {
        "key": "ctrl+shift+n",
        "command": "cursorDownSelect",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+shift+p",
        "command": "cursorUpSelect",
        "when": "editorTextFocus"
    }, 
    {
        "key": "ctrl+shift+f",
        "command": "cursorRightSelect",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+shift+b",
        "command": "cursorLeftSelect",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+shift+a",
        "command": "cursorHomeSelect",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+shift+e",
        "command": "cursorEndSelect",
        "when": "editorTextFocus"
    }
]
```
これをそのままコピペ。
それぞれのキーに対して、各方向に、テキストを選択状態にするよう既存のキーバインディングを上書きしています。

これで他のエディタと同じように`Ctrl + Shift + F`などで選択できる状態に！

よきVSCodeライフを！

# 参考記事
[VSCodeでテキスト選択（ctrl+shift+〇）のキーバインド登録方法](https://qiita.com/takewell/items/42808743951320403666)
RDKitでrdMolDraw2Dで生成した構造式画像をエクセルに出力する

### 背景
RDKitのPandasToolsを使えば構造式画像をエクセルに出力することができる。しかしこの場合Drawモジュールという見た目がイケてない方により生成された画像が出力される。今回PandasToolsをハックしてrdMolDraw2Dというイケてる方でもエクセルに構造式画像を出力する方法を調べたためメモっておく。

### 環境
- Windows10
- Python3.6
- RDKit 2018/9/2

### 方法
まず、必要モジュールのインポート。足りないものは事前にインストールしておく

```python
from rdkit import Chem
from rdkit.Chem import Draw, AllChem
from rdkit.Chem.Draw import rdMolDraw2D
from IPython.display import SVG
from rdkit.Chem import PandasTools
import pandas as pd
import numpy as np
from io import BytesIO
import copy
import xlsxwriter
from PIL import Image, ImageFilter
from cairosvg import svg2png
import argparse
```

次にrdMolDraw2Dによる構造式画像をByteIO形式で生成する関数を用意する。

```python
def generate_image(mol, size):

    image_data = BytesIO()
    view = rdMolDraw2D.MolDraw2DSVG(size[0], size[1])
    tm = rdMolDraw2D.PrepareMolForDrawing(mol)

    view.DrawMolecule(tm)
    view.FinishDrawing()
    svg = view.GetDrawingText()
    SVG(svg.replace('svg:', ''))
    svg2png(bytestring=svg, write_to='tmp/output.png')
    img = Image.open('tmp/output.png')
    img.save(image_data, format='PNG')

    return image_data
```

次に上の関数を用いてエクセルに出力する関数を用意する。PandasToolsの修正版である

```python
def save_xls_from_frame(frame, out_file, mol_col='MolCol', size=(300, 300)):
    margin = 60

    cols = list(frame.columns)
    cols.remove(mol_col)

    data_types = dict(frame.dtypes)
    workbook = xlsxwriter.Workbook(out_file)  # New workbook
    worksheet = workbook.add_worksheet()  # New work sheet
    worksheet.set_column('A', (size[0] - margin + 20) / 6.)  # column width

    # Write first row with column names
    c2 = 0
    worksheet.write_string(0, c2,  mol_col)
    c2 += 1

    for x in cols:
        worksheet.write_string(0, c2, x)
        c2 += 1

    c = 1
    for _, row in frame.iterrows():

        worksheet.set_row(c, height=size[1] - margin)

        # 画像の生成
        image_data = generate_image(row[mol_col], size)
        worksheet.insert_image(c, 0, "f", {'image_data': image_data})

        c2 = 2
        for x in cols:
            if str(data_types[x]) == "object":
                # string length is limited in xlsx
                worksheet.write_string(c, c2, str(row[x])[:32000])
            elif ('float' in str(data_types[x])) or ('int' in str(data_types[x])):
                if (row[x] != np.nan) or (row[x] != np.inf):
                    worksheet.write_number(c, c2, row[x])
            elif 'datetime' in str(data_types[x]):
                worksheet.write_datetime(c, c2, row[x])
            c2 += 1
        c += 1

    workbook.close()
    image_data.close()
```

さあ、お膳立ては整った。あとは呼び出すだけ。

```python
names = []
mols = []

for mol in Chem.SDMolSupplier("test.sdf", removeHs=False):
    mols.append(mol)
    names.append(mol.GetProp("_Name"))

df = pd.DataFrame(columns=["MolCol","NAME"])

df["NAME"] = names
df["MolCol"] = mols

save_xls_from_frame(df, "test.xlsx", mol_col="MolCol")
```

### 参考
- [PandasToolsソース](https://github.com/rdkit/rdkit-orig/blob/master/rdkit/Chem/PandasTools.py)
nodeでPOST RequestするときにURL encodeで投げてしまった。

lambdaで自作のPOST APIを叩こうとしたらうまくいかなかった。
結論から言えば、APIとしてはJSONのbodyしか対応していないのにurlencodeされたRequestを投げていた。
その備忘録

JSONは

```JSON
{ 
 "key1":"value1",
 "key2":"value2"
}
```
こんな感じなのだが、受け側で勝手に

```JSON
key1=value1&key=value2
```
みたいになってしまいJSON Parseのエラーを吐いていた。

Request側で

```javascript
let RequestJson =
{ 
 "key1":"value1",
 "key2":"value2"
};
```
としたとき

```javascript

let reqBody = JSON.stringify(RequestJson);
```

としなければならないのに

```javascript

let reqBody = querystring.stringify(RequestJson);
```

としていたようだ。
初歩的ミスすぎて気づくのに無駄に時間がかかってしまった。
Ubuntu 18.04LTSにmecab-pyton3をインストールする

# はじめに
mecab-python3をインストールしようと思いネットを漁っていたら10分ぐらいはまってしまいました。

# 環境

* Ubuntu18.04 LTS
* pyenv 1.2.9
* python 3.6.8

# 結論
僕の場合以下のコマンドをターミナルで打ったらできました。

```
sudo apt-get install mecab mecab-ipadic-utf8 libmecab-dev swig
pip install mecab-python3
```

# 参考文献
[mecab-python3(0.996.1d)のpip installでErrorとその対応方法(google colabの場合)](https://qiita.com/siraasagi/items/e07e0b271cb7cd679a70)
OSの定義とWindowsとMacOSとLinuxの違い

この記事ではOSの定義とWindowsとMacOSとLinuxの違いを紹介します。

### OS（オペレーティングシステム）の定義
CPUの入出力や同時並行処理といったものを管理するプログラムのことです。
ユーザー視点だと、ユーザーとハードウエアのインターフェースとして機能し、ユーザーに対してプログラムを実行する環境を提供するもののことである。
ハードウエア視点からだと、CPUやメモリといったハードウエア資源とプログラムやデータといったソフトウェア資源両方の有効活用を図り、ユーザー間の共有を実現するための制御プログラムのことである。

### WindowsとMacOSとLinuxの違い
クローズドソースソフトウエアかオープンソースソフトウェアかどうかという点に最大の違いがあります。
windowsとMacOSはクローズドソースソフトウエアで、Linuxのみオープンソースソフトウェアです。


* Linux・・・
Linuxはオープンソースソフトウェアです。
オープンソースソフトウェアはプログラムの中身が公開されているソフトウェアのことです。
そして、全ての人が利用・複製・配布する権限があります。
オープンソースソフトウェアの例として、ChromやAndroid(Linuxベースのスマホ用OS)があります。
Linuxは何かを作ったり、動かしたりすることの特化したOSです。
LInuxは1行コマンドを入力するだけでソフトウェアを導入できます。

* windows・・・
windowsは使いやすく、ゲームをしたりするのに特化したクローズドソースソフトウエアのOSです。Windowsのすべての動作はGUIからできるようになっている。
windowsで効率化・自動化の部分は低いです。
例としては、何かソフトウェアをインストールする場合、ブラウザ上の配布元のサイトから実行する必要があります。

* MacOS・・・MacOsはクローズドソフトウエアです。クローズドソフトウエアとはオープンソースソフトウェアの逆で、ソースコードを非公開としたソフトウェアで、改変や複製することを制限しています。MacOSはwindows同様使いやすく娯楽用途に向いていますが、どのOSよりも高価です。
RDKitで水素の付加または除去した際に新旧MOLオブジェクトの原子のインデックスを対応づける方法

### 背景
反応部位として原子のインデックスがSDFに登録されているとする。SDFを読み込んでその分子の構造を描画する際にそのインデックスで示される原子をハイライトしたいとする。読み込んだSDFをMOLオブジェクトに変換し、水素の付加または除去したMOLオブジェクトを生成すると、新しく作成されたMOLオブジェクトでは原子のインデックスが全く変わってしまうため、もともと反応部位として登録されていた原子をハイライトさせることができない。水素を付加または除去しても新旧のMOLオブジェクトの原子インデックスを対応づけたい。

### 環境
- Windows10
- Python 3.6
- RDKit 2018/9/2

### 方法
思いついた方法は、水素のあるMOLオブジェクトに対し、水素のないMOLオブジェクトを部分構造検索をする。構造検索の結果得られるリストには、水素のないMOLオブジェクトの各原子のインデックス順番に、水素のあるMOLオブジェクトの対応する原子のインデックスが得られる。

```python
# HありのMOLからHなしのMOL生成
mol_noh = AllChem.RemoveHs(mol)

if mol.HasSubstructMatch(mol_noh):
    patterns = mol.GetSubstructMatches(mol_noh)
```

上のpatternsにマッチングした部分構造が複数得られるため、最初に得られたリストを参照すればよい。
VSCodeを導入してみた


## 最近よくVSCodeと聞くので

普段は、Atomを使っています。ただ、VSCodeの話も聞くので試してみました。どっちが便利かは使ってみないとわからないですからね。

VSCodeは、Visual Studio Codeというマイクロソフトによって開発されているソースコードエディタです。マイクロソフトではあるものの、OSSであり、WindowsだけでなくMacでもつかえるし、Linuxでも使えます。オープンに使われることを望んでいるようですね。

## ダウンロードした

[Visual Studio Code \- Code Editing\. Redefined](https://code.visualstudio.com/)

上からダウンロードしました。

ダウンロードした「VSCodeUserSetup-x64-1.33.1.exe」を実行しましょう。なお、x64-1.33.1の部分は、その時のバージョンなので変わりますね。

## インストールした

ダウンロードしたexeファイルを実行してインストールしましょう。何も難しくなかったので画面に従って割愛します。

## 実行してみた

で、実行してみました。もうすでにいろいろ作っているので、初期の頃の画像はないのですが、見た目はAtomとほとんど同じように使えますね。

[![Image from Gyazo](https://i.gyazo.com/0f14e39613266e531fb56fe04ea5a5c1.png)](https://gyazo.com/0f14e39613266e531fb56fe04ea5a5c1)

### 見た目は好き好きかなあ。個人的にはAtom。

左側にExploreをはじめ、Gitや拡張機能などがアイコンで表示されています。拡張機能を導入することで増えていくようですね。
Atomは、この部分がExploreだけなので、シンプルさはAtomかもしれませんが、Gitとかは右下だったり右側だったりと散漫としているので、整理されているのはVSCodeかもしれません。

**とりあえず左側見とけ！** という姿勢は嫌いじゃありません。

ちなみに、プレビューはAtomでもVSCodeでも用意されているので差異はありませんかね。

### 動作性はVSCode

VSCodeのほうが圧倒的に軽いです！　というか、安定さがあって不安感が全く無いですね。Atomのほうは、なんか重くなったりしたり、突然落ちたりするのでちょっと怖いんですよねえ。

### デバッグは断然VSCode

Atomでも拡張機能を入れればできるんでしょうけど、VSCodeはほぼほぼデフォルトでできるように設計されていますね。コードを組みたい自分としては、かなりの高評価です。

なにより **PowerShellとの親和性が高い** 。PowerShell信者なので、結構ガッツリやりたいんですけど、Atomだと難しいんですよねえ。かといって、PowerShell_Iseもそのためだけに立ち上げるのはなんだかなあ。と思っていました。

VSCodeはその分、自然と使えるのでバッチリですね！　この時点で私としてはVSCodeに軍配です。

[![Image from Gyazo](https://i.gyazo.com/eb4c920c20e9c0a1410c9d324cd9b6e5.png)](https://gyazo.com/eb4c920c20e9c0a1410c9d324cd9b6e5)

いいですねえ。もうシンプルにデバッグしてくれって、構図でとてもいいです。

### Git, GitHubの使いやすさはAtom

これは趣味な気がしますが、個人的にはAtomに軍配です。拡張機能が優秀というのもあるんですけれど、VSCodeのGitに関する捜査官がシンプルすぎて、とっつきにくいんですよね。GUIとしては、正直使いづらいです。

その点、Atomはほとんど説明なしかつワンクリックでPushもfetchもStageChangeも簡単です。直感で操作ができるというのは重要です。

[![Image from Gyazo](https://i.gyazo.com/7e9267eabb08918122221b85d967bb13.png)](https://gyazo.com/7e9267eabb08918122221b85d967bb13)

Atomは右側だけ見ていれば、Gitの状況がすべてわかるのでとてもいい。VSCodeは、なぜか下から上に向かってStageingしていくのが気に食わない。あと、直近のCOmmit履歴が見れないのはBADです。拡張機能あるかもだけど。

一方、VSCodeにもいいところはあります。Shift + Ctrl + P でコマンドを打てる状態になるので、そこからGitのコマンドを打てるのです。というか、VSCodeでGit使うならそっちのほうが心理的に楽なんだよなあ。完全に自分の裁量でコマンドを打てるので、変なバックグラウンドが動かないかの心配がいらないし。

もっとも、GitでGUI使いたいなら[Git \- Downloading Package](https://git-scm.com/download/win)のほうがいいです。どうしても、日本語とか文字コードとかが微妙なんだけど、やっぱりGUIとしてのGitアプルとしては使いやすいんですよね。

## 結論

しばらく、VSCodeをメインで使おうと思います。軽いのとPowerShellとの親和性に惚れました。

ただ、ひとつわからないのは、Workspaceの概念。これって、どういう概念なのかな。単純に、作業領域を分割している？という簡単な話ではなさそうです。フォルダで分けてれば十分なんだけども。

WorkSpaceの有効な活用方法をご存知でしたら教えてください。
DCGANをなるべくやさしく解説してChainerで実装してみよう

#どうしたの
皆もすなるDCGANというものを，我もまたしてみんとてするなり．

ということで， 今でもガンガン活用が進んでいる(?)GANないしDCGANについて(自分の理解を深めるためにも)気持ちをふわっと解説して，実装してみたい！
とか言ってたら下書きを放置して半年以上経ってしまってつらいきもちです

#環境
OS: Ubuntu 18.04 LTS
Python: 3.6.4
Chainer: 1.24(事情により非常に古くなっております．最新版に合わせたコードは今度書く…たぶん)

#GANについて
GAN(Generative Adversarial Network ; 敵対生成ネットワーク)とは，[Goodfellowらによる論文](http://papers.nips.cc/paper/5423-generative-adversarial-nets.pdf)で発表されたアイディアです．

かんたんに言うと
<dl>
<dt>Generator(贋作屋)</dt>
<dd>ランダムな配列から訓練データに似せたデータを作るネットワーク</dd>

<dt>Discriminator(鑑別器)</dt>
<dd>元々の訓練データとGeneratorが作った偽物データを読んで「訓練データor偽物」を判定するネットワーク</dd>
</dl>
の，ふたつのネットワークを用意して，以下の式で表されるmin-maxゲームをさせます．
ここに，$E[x]$は$x$の期待値，$x$は用意した訓練データ，$G(z)$はGeneratorが(用意した訓練データに似せて)作った偽物．$D(x)$は Discriminator が $x$ を本物だと思う確率です．

```math
\min_G\max_DV(D,G)=E[\log D(x)] + E[1 - \log D(G(z))]
```

直観的な説明をします．$D$が*正しい判断*をできれば$logD(x)も1-logD(G(z))$も大きい値を取り，$V(D,G)$は大きくなりますし，*誤った判断*をすれば逆に小さくなります．
Generator からすれば$V(D,G)$は小さくなって欲しいし，Discriminator からすれば大きくなって欲しい．こんなイタチごっこを繰り返すのが GAN のコンセプトです．

#実装
しました．
[github](https://github.com/akjgskwi/DCGAN_implement)に細かい層の構成とかは readme に載っているので（~~書くの面倒だった~~）見てやってください．
UnityをRiderで書くときのgitignoreの設定

## UnityをRiderで書くときのgitignoreの設定
Riderを使ってUnity開発する場合、通常とは異なるファイルが生成されます。それらに対応した、僕が使用している.gitignoreがこちらになります。参考にどうぞ。

```
# Created by https://www.gitignore.io/api/unity
# Edit at https://www.gitignore.io/?templates=unity

# Jetbrain Rider Cache
.idea/
Assets/Plugins/Editor/JetBrains*

# Visual Studio Code
.vscode/


### Unity ###
[Ll]ibrary/
[Tt]emp/
[Oo]bj/
[Bb]uild/
[Bb]uilds/
Assets/AssetStoreTools*

# Visual Studio cache directory
.vs/

# Autogenerated VS/MD/Consulo solution and project files
ExportedObj/
.consulo/
*.csproj
*.unityproj
*.sln
*.suo
*.tmp
*.user
*.userprefs
*.pidb
*.booproj
*.svd
*.pdb
*.opendb
*.VC.db

# Unity3D generated meta files
*.pidb.meta
*.pdb.meta

# Unity3D Generated File On Crash Reports
sysinfo.txt

# Builds
*.apk
*.unitypackage

# End of https://www.gitignore.io/api/unity
```

この.gitignoreは、こちらを参考にしました。
https://github.com/JetBrains/resharper-rider-samples/blob/master/.gitignore
## 終わりに
私は現在、Web3のサービスの開発をしています。詳しくはこちらの記事をご覧下さい。
        [無料でイーサリアムが当たる、Web3時代の寄付サイトを作った話](https://note.com/kenroda/n/n814347fbdcd7)
golang.tokyo#23レポ 2019/04/19 〜絶対に分かるポインタ編〜

はじめまして。まいたけ([@maitaketurn](https://twitter.com/maitaketurn))です。
普段は都内のベンチャーでGo,Pythonなど書いています。

golang.tokyoに参加してきました！（初勉強会参加でした）
自分の復習も兼ねてレポってみます〜

## 絶対に分かるポインタ / tenntennさん
- ポインタとは
  - 変数の格納先を表す値：破壊的な操作をする際に使用する
  - ポインタのポインタもある：**Tなら*Tのポインタのこと。

- 型の表記方法
  - 名前のついた型:組み込み型など
  - 型リテラル：識別子（名前）がついていない型。スライス、構造体など。型リテラルのポインタ型も定義できる。

- ポインタ演算
  - &:ポインタ値を取得する
  - *:ポインタが指す先を取得する

これだけ！シンプル！！

例）

``` go
package main

import (
    "fmt"
)

func main() {
    type T *****************int
    var t ***T
    fmt.Println(&t)
}

```
出力結果

```
0x40c128
```

tのアドレスが出力される。*の数は関係ない

### ポインタはなぜ必要？
代入だとコピーになる。

``` go
p := struct {
		age  int
		name string
	}{age: 10, name: "Gopher"}

	p2 := p // コピー
    p2.age = 20

	println(p.age, p.name)
	println(p2.age, p2.name)
```
出力結果

```
10 Gopher
20 Gopher
```

p2にの値を変更したとしても、pの値は変更されない。
### ポインタが絡んでくる話
- 内部でポインタを使っているデータ型
  - スライス
  - マップ
  - チャネル


``` go
func main() {
	ns := []int{10, 20, 30}
	ns2 := ns
	ns[1] = 200
	println(ns[0], ns[1], ns[2])
	println(ns2[0], ns2[1], ns2[2])
}
```
出力結果

```
10 200 30
10 200 30
```
ポインタを使っているので、nsの変更はns2にも反映される。破壊的な操作。

### スライスについて
構造体で定義されている。以下をフィールドとして持つ
  - スライス元となる配列のポインタ
  - length
  - capacity

- appendの挙動
  - capacityが足りる場合：新しい要素をコピーしてlengthを更新する
  - capacityが足りない場合：元のcapacityの2倍程度の領域を新たに確保する


``` go
package main

import "fmt"

func f(ns []int){
	ns[1] = 200
	ns = append(ns,40,50)
}

func main() {
	ns := []int{10, 20, 30}
	f(ns)
	fmt.Println(ns)
}
```
出力結果
`[10 200 30]`
appendした際にcapacityが足りないので、新しくアドレスが振られるため。
appendしたら戻り値を新しい代入すれば40,50を追加できる。

``` go
package main

import "fmt"

func f(ns []int) []int{
	ns[1] = 200
	ns = append(ns,40,50)
	return ns
}

func main() {
	ns := []int{10, 20, 30}
	ns2 := f(ns)
	fmt.Println(ns)
	fmt.Println(ns2)
}
```
出力結果
```
[10 200 30]
[10 200 30 40 50]
```

### 参考
https://speakerdeck.com/kaznishi/180713-lt
https://qiita.com/hitode7456/items/562527069e13347b89c8

### まとめ
ポインタの根幹の考え方自体はシンプル。
スライスやマップなども内部にポインタを持っているので、ポインタが分かればそれらも分かる！（はず）

まだお一人目の発表分しか書いてないのですが、長くなってしまったので他の発表者の方の内容については別記事にて！
前回の記事の補足　Pythonのアウトプット

こんにちは
[未来電子テクノロジー](https://www.miraidenshi-tech.jp/intern-content/program/)
でインターンをしているodattiです。

Pythonの勉強をしています。

前回の記事では
md や cdの意味について触れたのですが、今回はそれに補足する形でアウトプットします。

#cd..
ひとつ前のディレクトリに戻ります。
ちなみに、cd../..でディレクトリを二つ前に戻るそうです。

#ディレクトリでサーバーを立ち上げるときの注意
なぜ僕が

```powershell

cd..
```

について最初に言及したのか。
それは、ディレクトリでサーバーを立ち上げるときは
「立ち上げたいディレクトリの一つ前に戻らなければならない」
からです。

例えば、cgi-binでサーバーを立ち上げたいときにcgi-binのディレクトリでサーバーを立ち上げようとすると、

cgi-bin/cgi-bin/…

となってしまうからです。
サーバーを立てた場所からのパスだということがとても大切なのでした。
(ちなみにこのことさえ理解できていなかったために、サーバーを立ち上げるのにかなりの時間を費やしました)







P.S　今回の記事とはあまり関係ないのですが、Pythonって英語でニシキヘビっていう意味なんですね。Python関連の本の表紙に蛇が多い理由がわかりました笑
CSSセレクタについて


# CSSセレクタとは

```css
.sample { font-size : 20px; }
```

ここでいう.sampleのところで、
CSSを適用する対象を指定することが出来ます。
対象の範囲が広いと、思いがけない所も対象となってしまうことがあるので
セレクタを指定するときは出来るだけ限定的に指定するのが大切です。


# 基本的な使い方

・全てのdevタグに適応します

```css
dev { color: #0000ff; }
```

# 全称セレクタ
全ての要素に適応します。

```css
* { color: #0000ff; }
```


# classセレクタ

適応するclassを記載するときは、.を頭に着けることで指定できます。

```css
.sample { color: #0000ff; }
```

# idセレクタ

適応するidを記載するときは、#を頭に着けることで指定できます。

・選択したidの要素にCSSを適応する。

```css
#sample { color: #0000ff; }
```

# 子孫セレクタ
指定した要素内の要素を指定する際に使用します。
使い方は半角スペースでセレクタを区切ります。

```css
.sample p { font-size : 20px; }
```

# 直下セレクタ
特定の要素の直下にある要素のみを対象にする際に使用します。
使い方はセレクタ同士を>で繋ぎ適応します。

```css
div.sample > p { font-size : 20px; }
```

# 間接セレクタ
特定の要素以降の兄弟要素に適応する際に使用します。
使い方はセレクタ同士を~で繋ぎ適応します。

```css
dev ~ span { font-size : 20px; }
```

# 隣接セレクタ
特定の要素の後続(同一階層)に出現する隣の要素を対象にする際に使用します。
使い方は要素同時を+で繋ぎ適応します。

```css
dev + span { font-size : 20px; }
```

# 属性セレクタ
任意の属性を持つセレクタを対象に適応する場合に使用します。
使い方は要素の後に[]で属性を指定します。

```css
div[#sample] { color: #0000ff; }
```

更に値を指定することも出来ます。

```css
div[#sample="test" ] { color: #0000ff; }
```
オブジェクトのある場所のUVを取得する

# こんな感じ

![textureCoord.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/249684/f16ca2b2-6cf5-2ece-8b42-6ff87e817d43.gif)
※画面をクリックして表示位置を変更してます。

# 手順

- Camera.main.ScreenPointToRay
 - スクリーンでタッチされた場所からRayを飛ばす
- Physics.Raycast
 - 飛ばされたRayとColliderとの当たり判定
- RaycastHit
 - ヒットしたオブジェクトの情報
- textureCoord
 - RaycastHitに設定されているテクスチャ座標（UV）

※↓にコード置いておいたので合わせて確認してみてください。

# その他メモ（調べておきたいことなど）

- MeshColliderでないと当たらない？(らしい
- Rayを飛ばさないとわからない？

# 参考
Splatoonの塗りみたいのを再現したい その５
http://esprog.hatenablog.com/entry/2016/05/08/212355

# ソースコード

```c#:MousePainter.cs

public class MousePainter : MonoBehaviour
{
    private void Update()
    {
        if (Input.GetMouseButtonDown(0))
        {
            // クリックされたスクリーンの位置からRayを飛ばす
            var ray = Camera.main.ScreenPointToRay(Input.mousePosition);
            RaycastHit hitInfo;

            // Rayとの当たり判定
            if (Physics.Raycast(ray, out hitInfo))
            {
                #region Use_textureCoord
                // シェーダにUVを渡す

                var material = hitInfo.transform.gameObject.GetComponent<Renderer>().material;
                    
                Vector4[] _Pos = new Vector4[2];
                    
                _Pos[0] = new Vector4(hitInfo.textureCoord.x, hitInfo.textureCoord.y, 0, 0);
                    
                material.SetVectorArray("_Pos", _Pos);

                #endregion Use_textureCoord
            }
        }
    }
}
```
プログラミング初心者のアルゴリズム第一歩

#はじめに
プログラミング初心者であるため、内容に誤りがあるかもしれません。
もし、誤りがあれば修正するのでどんどん指摘してください。
私は、現在未来電子テクノロジーでインターンを行なっています。
今回は、プログラミングを勉強する通過点であるアルゴリズムを勉強して、感じた第一歩についてお話しします。

#アルゴリズムとは
初め、アルゴリズムと聞くとなんのことか全くわかりませんでした。
調べたところ、アルゴリズムは、効率的に的確に答えにたどり着くための手段のことでした。
これを聞いて難しそうと感じましたが、やってみると納得する部分が多かったです。
より簡単に言うと、アルゴリズムは、数学のように問題を一番簡単に解く手段です。

#アルゴリズムを勉強するメリット
アルゴリズムを勉強する上でのメリットは、答えまでにたどり着くスピードが上がることです。
また、処理スピードも上がり、プログラミングをよりできるようになったと錯覚できます。
プログラミング初心者にとって、一番スピードが上がる必勝法だと思います。

#まとめ
今回は、アルゴリズムの詳細は、書いていません。
今後、書いていきたいと思います。
Xcodeで競プロを始めました（C++）

# 概要
結論；macOSにXcodeをインストールすれば簡単にC++で競プロを始められます！

面接体験記を見ていると、出されたロジックをホワイトボードにコーディングしてみろ、と言われるそうで。自分の身にいつ降り掛かってもいいように対策しようと思いました。
しかし現在やっているiOSの本を使ってもMVCの構造やライブラリの使い方が主で、例えばソートや探索木とかは一生触らないだろうなあと。
どうしたらいいかとふと思い調べてみると、どうやら競技プログラミングを触ってみるのが良いようで。教科書と違い実践的であるのが良い、身につくまでできる気がする。
サイトは日本語情報が多そうなATCoderを選択。挫折しないことがまずは大事。
# 言語はC++を選択
使う言語は触ったことは無いがC++を選択。
これは競プロ回答の6割以上がC++のため、回答を参考しやすいだろうという理由。
またC++だとXcodeがあれば済むというのが大きい。（新しいIDEを用意するのも億劫ですし…）

言語はとりあえず使ってみて分からないときに初めて調べる[「遅延評価勉強法」](http://blog.livedoor.jp/kensuu/archives/50555054.html)でやってみる。
Cと同じ感覚で使えるので、何かしら1言語やってたら学習コストは低いように思う。（今の所ですが）
# エディタはXcodeを使用
XCodeは簡単にBreakPointを貼れるので、デバッグしながら変数の値を確認できるのは嬉しいです。
## 参考
[1.2.2 Xcodeのインストールと簡単な使い方　((C++からのプログラミング入門
](https://qiita.com/Naggi-Goishi/items/0f02aad433f2ce796326)
[XcodeとC++で競技プログラミングするときの初期設定の一例](http://peroon.hatenablog.com/entry/2017/05/13/023529)
## ATCoder用の設定
Command Line Toolを選択
![-w735](https://i.imgur.com/MAyY87I.jpg)
言語に「C++」を選択。
![-w740](https://i.imgur.com/3EEF91V.jpg)
`main.cpp`と同じ場所に`input.txt`を作成。
![-w471](https://i.imgur.com/NcIpQXR.jpg)
`input.txt`をプロジェクトへ追加する。
![-w280](https://i.imgur.com/Fs0JHsb.jpg)
こうすると`input.txt`をXcodeから直接編集できるのでテストデータの入力が楽。
![-w719](https://i.imgur.com/Aa61JBR.jpg)
`input.txt`をコードから読み込めるように設定を行う。
`Edit Scheme`を選択
![-w402](https://i.imgur.com/7dwGuOd.jpg)
下記を先程の`input.txt`が格納されているディレクトリを指定する。
![-w896](https://i.imgur.com/EbYF9bh.jpg)
動作確認のコード。提出時は`//input from txt`を含めて下3行を削除するだけ。

# 使い回す用のコード

- コード部分だけに集中できるように、他の部分は何かしらで登録しておくと良いと思う。
- 私は下記をDashのスニペットに登録して使用している
    - [Dashのスニペット機能をちゃんと使う](https://qiita.com/hachi8833/items/5c195f1164ce7c5e65ab)
- ライブラリも必要に応じて追加する必要はありそう

```cpp
//  main.cpp
//  CppTest

#include <iostream>
#include <fstream>
#include <vector>
#include <algorithm>
using namespace std;

int main(int argc, const char * argv[]) {
    
    // input from txt （提出時にこの箇所は削除すること）
    std::ifstream in("input.txt");
    std::cin.rdbuf(in.rdbuf());
    
    // cinを高速にするためのおまじない
    cin.tie(0);
    ios::sync_with_stdio(false);
    
    /////////////////////
    // Write code below /
    /////////////////////
    
        
    return 0;
}
```
【Java】Progateで取り上げられていないJavaの基本まとめ~その１~

# 1. package

`class` についてはある程度イメージができているという前提で進めていきます。
よくクラスは設計図、インスタンスはその設計図をもとに実際に生成されたもの、とか説明されていますがクラスがわからなければググってください。
他のオブジェクト指向のプログラミング言語にも共通していると思います。

### packageとは何か
>
javaのプログラムの基本はクラスの作成から始まります。
単純なプログラムを作成していく場合は少ないクラスの利用だけですみますが、
大きなプログラムを作成していく場合はたくさんのクラスを利用していきます。
パッケージとはクラスやインタフェースの集りで、用途などで分類します。
javaではobjectクラスを筆頭に様々なクラスを用意されていますが、これらもすべてパッケージで管理されています。
パッケージが異なると同じ名前のクラスでも別のクラスとして扱われます。

引用元：http://www1.bbiq.jp/takeharu/java51.html


> 
Java™ のクラスはそれぞれ、あるパッケージに属しています。 どのクラスがどのパッケージに含まれるかは、Java ソース・ファイルの最初のステートメントに記述されます。 ソース・ファイルにパッケージ・ステートメントがない場合、そのクラスは名前のないデフォルトのパッケージに含まれると見なされます。


引用元:https://www.ibm.com/support/knowledgecenter/ja/ssw_ibm_i_71/rzaha/clpckdir.htm

### packageの特徴
・全てのclassはpackageに属している
・packageが指定されていない場合、デフォルトのpackageに属する
・関連するclassをpackageにまとめると開発の単位が明確になり管理しやすくなる、同一packageないからのアクセスのみ許可するなどの制限をかけられるといったメリットがある。
・package名の階層はディレクトリの階層に対応する
(`java.util.ArrayList` は`java/util/ArrayList.class` に対応している)

### classが属するpackageの指定方法

```java:
package java.lang;
```

`java.lang`に属することを宣言している。

### importとは
・本来classを一意に特定するためには、`完全修飾名`で記述しなければならない。
※`完全修飾名`=> package名を含めたto.java.code.sample.basic.Animalのような名前
・これを毎回記述せずに済むように、import命令を記述することでpackageを省略できる。
・import命令は一般的にpackage宣言の直後に記述する、らしい。


### import と *
```java:
import java.util.*;
```

この指定により、java.utilの直下のディレクトリ階層を全て指定することができる。


# 2.メンバ変数

= インスタンスフィールド、インスタンス変数に同じ。


# 3. 基本データ型と参照型

大枠で捉えるとするなら、変数の種類を分類すると`基本データ型`(=`プリミティブ型`、`値型`)と`参照型`(=`クラス型`)の2つに分けられる。

### 基本データ型とは

次の8種。

| 型 | メモリ領域 | 概要 |
|:--|:--|:--|
| boolean | 1bit | true or false |
| char  | 16bit  | Unicodeの一文字 |
| byte  | 8bit  | 符号付き整数 -128～127 |
| short  | 16bit  | 符号付き整数 -32768～32767 |
| int  | 32bit  | 符号付き整数 -2147483648～2147483647 |
| long | 64bit | 符号付き整数 約-922京～約922京 |
| float  | 32bit  | 浮動小数点数 |
| double | 64bit  | 浮動小数点数 |

>基本データ型の変数というのは、型によってその大きさ（bit数）がきっちり過不足無く決まっているということです。ということは、変数を宣言した時点でメモリ内のその変数の使用領域を過不足なく確保できるわけです。その決まった領域内に（その型の範囲内の値ならば）どんな値でも保持することができるんです。

参照元: https://nobuo-create.net/sanshougata/

・メモリに直接書き込まれる具体的なデータ値（数値や文字）を代入することができ、変数自体が値を持つ。
・参照型と異なりメソッドを持たない。
・全て小文字から始まる。



### 参照型とは

・基本データ型以外全てが参照型。
・配列やStringも参照型。
・参照型はオブジェクトを生成し、そのオブジェクトを参照するための値(=参照値)を変数に格納する。

参考URL: https://www.mlab.im.dendai.ac.jp/~yamada/java/reference/


# 4.定数

値の変更ができない変数。

```java:
final int COUNT = 4;
```

のように、先頭に`final`をつけ、大文字で表記する。
初投稿

未来電子テクノロジー(https://www.miraidenshi-tech.jp/intern-content/program/ )でインターンしているu141です。プログラミング初心者であるため、内容に誤りがあるかもしれません。
もし、誤りがあれば修正するのでどんどん指摘してください。

4月18日からProgateの初級コースを始めました。自分は一度このコースはやったことがあるのですが、習得する前に挫折してしまったので0からのスタートです。

初級編は割とスムーズに終えることができましたが、中級編のとくに後半のレッスン一覧以降の内容が少しわかりにくいと感じました。なので、しっかり覚えるためにも何度も手を動かしたいと思います。

これからがんばります！
Python3でキッチンタイマを作る

基本的に自分用のメモとして作成。

前回目覚まし時計を作ったので今度はキッチンタイマを作成。
（前回→[Python3で目覚ましを作る](https://qiita.com/Rxxx/items/d1f7d9a08dacf693b0a9)）

以下が作成したコード。

```python:KitchenTimer.py
import pygame.mixer
import time

#ファイル内変数
MINUTE_TO_SEC = 60


#アラーム処理
def Alert():
	print("時間です")
	Sound()
	
#音再生処理
def Sound():
	pygame.mixer.init() #初期化
	pygame.mixer.music.load('alerm1.mp3') #読み込み
	pygame.mixer.music.play(-1) #ループ再生（引数を1にすると1回のみ再生）
	input()
	pygame.mixer.music.stop() #終了	
	
#値の範囲確認
def CheckRange(num):
	if not 0 <= num <= 59:
		print("値が異常値です")
		exit()
	

#目覚まし設定時間取得
print("目覚ましをセットする時間を指定してください")
minute = int(input("分（minute）："))
sec = int(input("秒（sec）："))

#値の範囲確認
CheckRange(minute)
CheckRange(sec)

#待ち時間を秒に変換
wtime = (minute * MINUTE_TO_SEC) + sec

#タイマセット
print(str(minute)+"分"+str(sec)+"秒にタイマをセットしました")
time.sleep(wtime)
Alert()
```
time.sleepが秒しか指定できなかったので、分を秒に変換して無理やり時間カウントさせた。
本当はscheduleとか使ったりしたり、現在時刻からアラート時間を設定するとかした方がいいのかも。

<br>
実行したらこんな感じ
（入力値　1回目：2　2回目：1　）

```
pygame 1.9.5
Hello from the pygame community. https://www.pygame.org/contribute.html
目覚ましをセットする時間を指定してください
分（minute）：2
秒（sec）：1
2分1秒にタイマをセットしました
```
この場合「タイマをセットしました」と出てから2分1秒経過すれば「時間です」と表示され、alerm1.mp3が再生される。
目覚まし時計と同じで何かキー入力すれば音を停止できるようにしてます。



<br>
キッチンタイマとして動くけどちょっと無理やりすぎるなぁという作りだし、
59分59秒までしか設定できないのでこれ以上も設定できるように改善したいところ。

この変更はまた今度、気が向いたらやろうかな。

<br>
今回コードを書く上で色々調べてて知ったんだけど、Pythonって標準ライブラリで定数ないんだね。タプルはあるのに・・・なぜ？とびっくりした。
どこかの記事に、定数として変数を扱いたいときは変数名を大文字にする、というマナーがあると見ました。
練習用のコードだと変数名とかそういうの雑にしがちだけど、しっかり気を付けないとだね。
社員が増えてきてPOとPMを分けたくなった話


どうも、サイトビジットの横沢です。（[Twitter](http://bit.ly/2PkyJHK)）

最近社員の数が増えてきました。（ウレシイ）
いやー社員も増えて売上上がって会社も成長してウハウハだぜー！！！！と言うわけにもいかないのが世の常です。

10名ちょっとだったのですが、社運を賭けた全員人事により30名程度の規模になりました。
そして増えたエンジニアは1名。

そうです。
割合が違う。
いや全然違う。

つまり困るのは***エンジニアへの依頼の数は増える***のに肝心の***エンジニアの数が足りず***、依頼を捌き切れなくなり事業の成長スピードを阻害してしまうと言うことです。

これは由々しき事態です。

# 問題点
上記の通り、依頼数は増えたけど依頼を捌き切れなくなってしまいました。
エンジニアのリソースは有限なので全てのタスクを消化することは出来ません。


少し前までは僕が全ての依頼に対して工数・重要度・緊急度から優先順位をつけてエンジニアの方にご依頼していたのですが、人が増えていくにつれて重要度・緊急度を把握できなくなってきました。

- この依頼を達成した後に、どこにどのくらいのインパクトが出るかよく分からない***（重要度）***
- この依頼を達成できないと、どこにどのくらい迷惑が掛かるかよく分からない***（緊急度）***

期限日を入れてもらったりしていますが、基本的には依頼者はこのタスクに関して、「超重要！超緊急！マジ卍！」というテンションで依頼してくることがほとんどなので、マジなところどうなの？と言うところを把握するのは意外と難しいです。

なので、それらを全て正確に優先順位決めて要件定義してエンジニアに依頼するとなると僕のリソースが足りません。


全部チケットに詳細を書いてもらえばいいじゃないかとなるんですが、「チケット作るのがめんどくさくて依頼しない」みたいになったら本末転倒です。


# 解決策

大事なことは ***優先順位を正確に決めること*** です。
そのためにPOを新たに設置し、PMと分業することにしました。

## 用語整理

会社によって役割とか違うと思いますが、弊社では以下のような分類にしました。

- PO：プロダクトオーナー
    - タスクの優先度決め
    - 要件定義
- PM：プロダクトマネジメント
    - エンジニアのリソース管理
    - 仕様設計

要は

- タスクのことをPOに聞いたら `やりたい事` とか `それによって得られる効果` が返ってくる
- タスクのことをPMに聞いたら `現状の進捗` とか `リリース予定日` が返ってくる

と言う感じです。


# やり方
弊社ではTrelloを使ってカンバン方式でタスクの運用をしています。
<img width="1280" alt="Screen Shot 2019-04-21 at 22.20.21.jpg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/75102/6453d5fa-4055-bc3d-6fee-d5a98c773b18.jpeg">

カンバンには要件の他に、エンジニアさんが要件を細かくチケットにしたものも含まれています。（1チケットの工数は8時間以内くらいにしてねとお願いしてあります）

このカンバンをPOに見てもらい優先度を逐一決めていただきます。

1. 要件に当たるものは一番左の `Priority List` にストック
2. 毎週POとPMで優先順位, 進捗MTGを行う
3. POは `Priority List` の `効果・要件の把握` を行う
4. PMは `Priority List` の上から `仕様設計・工数見積` を行う
5. PMは `エンジニアのリソース状況の把握`, `スケジュール管理` を行う


POとしては `利害関係があまりなく`, `全体を俯瞰できる` そんな人が理想です。

現状は効果の検証中ですのでまた追記します。

# まとめ
1. タスクが捌き切れなくなったら気合じゃなくて優先順位決めよう
2. あなたのせいじゃないのでみんなにヘルプ求めよう
HTMLとCSSだけで連番を追加するには？

# 初めに
何かしらのウェブページをコーディングしている時、連番が必要な場合があると思います。
手動でつけたり、JavaScriptやバックエンド側で生成する方法も回答ですが、
***HTML又はCSS***だけで連番の追加は可能です。

自分もつい先日知ったので、ここでまとめたいと思います。

# リスト（箇条書き）で表せそうなコンテンツの場合
`ol`要素と`li`要素でlist形状にしましょう。

##少し詳しく
`ul`要素を使って連番をつけているコードがありますが、あまり意味がないです。
`ol`要素というのがありまして、これは***項目の順序付きリスト***を表します。
また、大抵はブラウザ上で連番ありの状態で表示されます。
連番を振りたい時は、順序に意味のあるリスト（箇条書き）だと思いますので、HTMLとしても意味のとおる`ol`を使用するのが、簡単でHTMLとしても正しいコーディングだと思います。

##実コードのサンプル
###html

```html
<ol>
  <li>aaa</li>
  <li>aaa</li>
  <li>aaa</li>
</ol>
```

###結果

```
1.aaa
2.aaa
3.aaa
```

`ol`を使用しても連番が表示されない場合は、ページ全体のstyleをresetしたり統一する為のstyleで、連番を表示しないようにしている可能性があるります。
この場合は、styleの状況を確認して、`ol`か`li`に`list-style: decimal`を追加してください。

参考：https://developer.mozilla.org/ja/docs/Web/CSS/list-style-type

#見出しみたいなlist以外のものに連番を振りたいです。
今回の本題です。
listの場合は`ol`でいけますが、見出しや普通の文章の場合は別のやり方になります。

使用するものは、***CSSカウンター***とよばれるものです。
styleは、
`counter-reset `
`counter-increment`
になります。

## サンプル
<p class="codepen" data-height="265" data-theme-id="light" data-default-tab="css,result" data-user="H_Naito" data-slug-hash="vYOOvxL" style="height: 265px; box-sizing: border-box; display: flex; align-items: center; justify-content: center; border: 2px solid; margin: 1em 0; padding: 1em;" data-pen-title="CSS counter">
  <span>See the Pen <a href="https://codepen.io/H_Naito/pen/vYOOvxL">
  CSS counter</a> by H.N (<a href="https://codepen.io/H_Naito">@H_Naito</a>)
  on <a href="https://codepen.io">CodePen</a>.</span>
</p>
<script async src="https://static.codepen.io/assets/embed/ei.js"></script>


##少し詳しく
CSSカウンターはCSSが管理する変数で、CSSルールが何回使用されているかを追跡します。
これを表示する事で、連番がふられているように見せます。

`counter-reset`はCSSカウンターに対して、与えられた値（デフォルト:0）で初期します。
`counter-increment`は、指定された値（デフォルト:1）でカウンターを増減させます。


##コーディングの流れ
1.連番を振りたいセクション（not section要素）の親要素に、`counter-reset`を使用してカウンターを設置/初期化します。
2.`counter-reset`を設定した要素の子/孫要素の内、連番を振りたい要素に`counter-increment`を設定します。
3.`content`を使用して連番を表示します。


##コード

###CSS

```css

.sample1 {
  /* 'hoge' というカウンターを0で初期化 */
  counter-reset: hoge;
}

h3::before {
  /* hogeカウンターの値に1(デフォルト値)を加算 */
  counter-increment: hoge;
  /* 表示　なおカンマを追加してます */
 content: counter(hoge)", ";
}

.sample2 {
  /* 10で初期化*/
  counter-reset: huga 10;
}

h4::before {
  /* -1していく */
  counter-increment: huga -1;
  /* （）付で表示 */
  content: "("counter(huga)") ";
}

```
###HTML

```HTML
<div class="sample1">
  <h3>Introduction</h3>
  <h3>Body</h3>
  <h3>Conclusion</h3>
</div>

<hr>

<div class="sample2">
  <h4>Introduction</h4>
  <h4>Body</h4>
  <h4>Conclusion</h4>
</div>
```

###結果

```
1, Introduction
2, Body
3, Conclusion

(9) Introduction
(8) Body
(7) Conclusion
```

###カウンターは入れ子にする事もできます
詳細はこちらです。

CSS カウンターの使用：カウンターの入れ子
https://developer.mozilla.org/ja/docs/Web/Guide/CSS/Counters#Nesting_counters

---
#参考
CSS カウンターの使用
https://developer.mozilla.org/ja/docs/Web/Guide/CSS/Counters

counter-reset
https://css-tricks.com/almanac/properties/c/counter-reset/

counter-incrementでリストではない要素にも連番を振る
https://qiita.com/ymk83/items/31ff9ee30d8fabdf2616
cv::parallel_for_が扱いにくい（わかりにくい）ので解説+扱いやすいラッパー関数を作ってみる

# tl;dr
cv::parallel_for_は、実行環境ごとにバックエンドが選ばれるので実行環境を考えず使える。しかし、
OpenCVオフィシャルサイトのHow to use the OpenCV parallel_for_ to parallelize your code](https://docs.opencv.org/4.1.0/d7/dff/tutorial_how_to_use_OpenCV_parallel_for_.html)
のサンプルコードがわかりにくい。もしfor文の並列処理をOpenMPで書くなら、

```c++
#pragma omp parallel for
  for(int icx= 0,idx<100000,idx++){
    //何かの処理
  });
```
と同様に書きたいだけなのに・・・Rangeって何だ？どうやって使う？ってことで解説し、扱いやすいラッパー関数も作ってみた。ちなみに、もう2019年、functorは使わずラムダ式でいいでしょ。OpenCV4.0からc++11必須になったことだし。


# サンプルコード
以下のような関数を用意して使えば、ラムダ式を使うことになるがOpenMPと同様でわかりやすい。

```c++
#include <thread>　//std::thread::hardware_concurrency()をコールするため

template<class FUNC>
void paral_for_idx(int st, int ed, FUNC func)
{
  int   num_cpu = std::thread::hardware_concurrency();//論理cpu数取得
  int nstripes = (ed - st + num_cpu -1) / num_cpu;
  cv::parallel_for_(cv::Range(st, ed),
                    [&func](const cv::Range& range) {
    for(int idx = range.start; idx < range.end; idx++) {
      func(idx);
    }
  },nstripes);
}

//使い方1
paral_for_idx(0,100000,[&](int idx){
  //何かの処理
});

//使い方2　画像処理
Mat3b mat;
paral_for_idx(0,mat.rows,[&](int y){
  for(int x=0;x<mat.cols;x++){
    //何かの処理　←mat(y,x)で画素値を参照できる
  }
});
```

# 解説
1つめのポイントは、paral_for_idxのラムダ式に渡される引数を一つにしたことで、記述しやすい。
2つめのポイントは、paral_for_idxの中でnstripesを計算し、引数として渡していること。cv::parallel_for_のラムダ式は引数にレンジを渡すので、このようにcpu数で割って切り上げた値をnstripesとして設定すると、cv::parallel_for_が連続してまとまった単位で処理してくれる。
cv::parallel_for_は、nstripesがデフォルト値のままだとどうも１単位ずつになるようで、例えば、使い方２の場合行ごとに別スレッドになってしまい、キャッシュ効率が悪い。上下画素も参照するフィルタ処理でキャッシュ効率を上げるなら、当然、近い行は同じCPUが同一スレッドで処理したほうがよい。
ちなみに、今回のnstripesの計算は「何かの処理」が同じ処理時間であることが前提なので、箇所によって処理時間が変動する処理ならnstripesを小さめにとって、スレッドの粒度を小さくし、解放されたCPUから次の処理を随時こなすようにしたほうがよい。ただ、そこまで制御したいならOpenMPでDyanamic指定を加えたほうがよいのかも。結局、OpenMPでも他の並列化フレームワークでも、最速を目指すなら環境とデータ特性に合わせて最適な並列化コードにチューニングする必要がある。環境を考えず、お手軽に使いたいなら、cv::parallel_for_を使ったほうが楽で、そのときparal_for_idxようなラッパー関数を用意しておくと、キャッシュ効率がよく、関数としても使い勝手がよい。
Colaboratory セッション切れ対策のメモ

## はじめに
Colaboratoryで長時間の学習などを行う場合、90分セッション切れ対策し
12時間完走するための方法のメモ。
他の方のQiita記事を組み合わせただけの他人の褌記事です。

## 方法
スクリプトかブラウザアドオンで90分以下のスパンで更新してやれば良い。
（自分はアドオンの方をやってます）
https://qiita.com/enmaru/items/2770df602dd7778d4ce6

しかし、セルにOutput（ログ）があると、ページに更新されたとみなされ
「変更あるけど更新していいの？ねえねえ？」と聞かれてリロードされない。

なので、以下のどちらかをする。

- そもそもログを出さない
- [スプレッドシートなどにログを出力する（セルには出さない）](https://qiita.com/Hidekazu-Karino/items/5201fce7249693357602)

ログが残らないのは不便なので、後者が良さそうに思う。

…でも私は今、実装が楽な方を取ってログを出していない。。

### 追記
このライブラリ良さそう。
標準出力出さなくして、Gドライブ上にログ吐くようにしてやればきっと…
https://qiita.com/k8uwall/items/07ace17382b454b996a7
東京大学大学院情報理工学系研究科 創造情報学専攻 2016年度 実技試験

東京大学大学院情報理工学系研究科 創造情報学専攻の2016年度 実技試験（プログラミング）の解答例（Python3）です。
https://www.i.u-tokyo.ac.jp/common/file/edu/course/ci/2015-8-program.pdf

※公開元ページは[こちら](https://www.i.u-tokyo.ac.jp/edu/course/ci/admission.shtml)
※記載の内容は筆者が個人的に解いたものであり、正答を保証するものではなく、また東京大学及び本試験内容の提供に関わる組織とは無関係です。

#(1)
```python
mport sys
  
a = sys.argv[1]
l = len(a)
i = 1

s = 0
for c in range(l):
    n=4**(l-i)*int(a[c])
    #print(n)
    s=s+n
    i=i+1
print(s)
```

#(2)
```python
import sys

a = sys.argv[1]
l = len(a)
i = 1

ds = {'a':0,'b':1,'c':2,'d':3,'e':4,'f':5,'g':6,'h':7}
s = 0
for c in range(l):
    n=len(ds)**(l-i)*int(ds[a[c]])
    #print(n)
    s=s+n
    i=i+1
print(s)
```

#(3)
```python
import sys
  
a = sys.argv[1]
r = {'I':1,'IV':4,'V':5,'IX':9,'X':10,'XL':40,'L':50,'XC':90,'C':100,'CD':400,'D':500,'CM':900,'M':1000}

def putChars(n, cs=""):
    for k, v in sorted(r.items(), key=lambda x: -x[1]):
        if (v<=n):
            cs = cs + k
            if (n-v==0):
                return cs
            else:
                return putChars(n-v,cs)
            break

ret=putChars(int(a))
print(ret)
```

#(4)
```python
import sys

a = sys.argv[1]
l = len(a)
r = {'I':1,'IV':4,'V':5,'IX':9,'X':10,'XL':40,'L':50,'XC':90,'C':100,'CD':400,'D':500,'CM':900,'M':1000}
sum = 0
c = 0
while(1):
    try:
        n1 = r[a[c]]
        n2 = r[a[c+1]]
        n3 = r[a[c+2]]
        if (n1>n2 and n3>n2):
            nx = n1-n2+n3
            sum = sum + nx
            c = c + 3
            if (c>=len(a)):
                break
            else:
                continue
    except IndexError:
        try:
            n1 = r[a[c]]
            n2 = r[a[c+1]]
            if (n2>n1):
                nx = n2-n1
                sum = sum + nx
                c = c + 2
                if (c>=len(a)):
                    break
                else:
                    continue
        except IndexError:
            pass

    try:
        ps = a[c] + a[c+1]
    except IndexError:
        ps = a[c]
    try:
        r[ps]
        c = c + 1
    except KeyError:
        ps = a[c]
    sum = sum + r[ps]
    c = c + 1
    if (c>=len(a)):
        break
print(sum)
```

#(5)
(3)と同じなため省略。

#(6)
(4)と同じなため省略

#(7)
```python
import sys
  
a = sys.argv[1]
a = a.split(' ')
l = len(a)
ds = {'one':1,'two':2,'three':3,'four':4,'five':5,'six':6,'seven':7,'eight':8,'nine':9,'ten':10,'eleven':11,'twelve':12,'thirteen':13,'fourteen':14,'fifteen':15,'sixteen':16,'seventeen':17,'eighteen':18,'nineteen':19,'twenty':20,'thirty':30,'fourty':40,'fifty':50,'sixty':60,'seventy':70,'eighty':80,'ninety':90,'hundred':100,'thousand':1000}

def getUpper(si):
    i = si-1
    while(1):
        if (i<0 or ds[a[i]]>ds[a[si]]):
            break
        i = i -1
    return i+1

def calcPartial(si, ei):
    if (si==ei):
        return ds[a[si]]
    else:
        i = si - 1
        sum = 0
        while(1):
            sum = sum + ds[a[i]]
            if (i==ei):
                break
            i = i - 1
        return sum*ds[a[si]]

sum = 0
c = l-1
while(1):
    gu = getUpper(c)
    cp = calcPartial(c,gu)
    c = gu - 1
    sum = sum + cp
    if (c<0):
        break
print(sum)
```
Herokuでwebサービス公開方法と削除方法

###heroku-cilをインストール###
```
$ wget https://cli-assets.heroku.com/heroku-linux-x64.tar.gz -O heroku.tar.gz
$ sudo mkdir -p /usr/local/lib/heroku
$ sudo tar --strip-components 1 -zxvf heroku.tar.gz -C /usr/local/lib/heroku
$ sudo ln -s /usr/local/lib/heroku/bin/heroku /usr/local/bin/heroku
```
###ターミナルでログイン###
```
$ heroku login -i
```
- Heorkuに登録したemail,passwordを入力する

####アプリ作成####
```
$ cd messge-board
$ heroku create message-board
```
**アプリが作成されたか確認**

```
$ heroku apps
```
**gitにリモートリポジトリが作成されているか確認**

```
$ git remote -v
```

####設定変更####
- Herokuの標準DBがPostgreSQLなため設定が必要

#####gemfile#####

- Production環境で、**pg**を使うとこを指定
- **pg**とはrailsとPostgreSQLを連携するためのGem

```rb
group :production do
  gem "pg", ">= 0.18", "< 2.0"
end
```
```
$ bundle install --without production
```

#####(config/database.yml)#####
- production環境の設定を**PostgreSQLに変更


```rb
production:
  adapter: postgresql
  encoding: unicode
  pool: 5
  database: message-board_production
  username: message-board
  password: <%= ENV['MESSAGE-BOARD_DATABASE_PASSWORD'] %>

```


####デプロイ####
``` 
$ git add .
$ git commit -m "for heroku"
$ git push heroku master
$ heroku run rails db:migrate
```

###アプリの削除###

```
$ heroku apps:destroy --app アプリ名
```

- もう一度アプリ名を入力する
- アプリとリモートリポジトリが削除される

####ついで####
```
 Warning: heroku update available from 7.25.0 to 7.29.0.

```
これは新しいバージョンにアップデートしてね！と言われている

```
heroku update
```
これでOK!
vue.js 遅延ルーティング キャッシュ削除も。

いやー引くほどハマった。
遅延ローディングのまとめ。

・node.js最新か？ (yumだと古いの入るので注意)
・npm最新か？
・node_modules を削除
・package-lock.json を削除

そんでもって再度インストールね。


参考
https://qiita.com/ykatsu/items/e373e8479f6c9a832f5d



キャッシュが残るので、デバッグはChromeシークレットモード。
キャッシュをオフにしてやる。

# ここまで理解してから次へ。

.babelrc は新規作成すること。

```.babelrc

{
  "plugins": ["@babel/plugin-syntax-dynamic-import"]
}



```


webpack.min.js は サーバーから vim で直接変更する！
FTP使ったりパーミッション変更するとバグるので。

キャッシュ対策も追加。
hash ってやっとくことで、キャッシュされなくなる。

```webpack.mix.js


const mix = require('laravel-mix');


mix.webpackConfig({

    output: {
        chunkFilename: 'js/chunks/[name]-[hash].js',
//chunkFilename: 'js/chunks/[name].js',
        publicPath: '/'
            }
});


//読み込みたいフォルダを指定しておく
mix.js('resources/js/app.js', 'public/js','public/js/chunks/').version()
     .autoload({
         "vue": ['Vue', 'window.Vue']
     })

    .sass('resources/sass/app.scss', 'public/css');

```




```vue.blade.php

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="utf-8">
    <link href="{{ mix('css/app.css') }}" rel="stylesheet">
</head>
<body>
<div id="app" v-cloak>
        <router-view></router-view>
</div>

<script src="{{mix('js/app.js')}}"></script>
</body>
</html>

```

```Top.vue

<template>

    <div>
        <router-link to="/layout">レイアウトに移動</router-link>
    </div>

</template>

<script>
    export default {
        title: 'top'
    }
</script>

```


```Layout.vue


<template>



    <div>

        移動成功！

    </div>


</template>
<script>

    export default {

    }
</script>


```


```app.js

import VueRouter from 'vue-router';
Vue.use(VueRouter);


const Top = () => import('./components/Top.vue');
const Layout = () => import('./components/Layout.vue');

var routes = [
    { path: '/', component: Top},
    { path: '/layout', component: Layout , meta: { title: 'レイアウト' }},
];

const router = new VueRouter({
    mode:'history',
    routes,
});

var app;
app = new Vue({
    el: '#app',
    router,
});




```


一応キャッシュファイルがてんこ盛りできるとあれなので。

```package.json


{
    "scripts": {
        "predevelopment": "npm run clean",
        "clean": "rimraf public/js/chunks",

        "dev": "npm run development",
        "development": "cross-env NODE_ENV=development (略)"
    },
}


```

npm run clean で ゴミファイルすべて削除できちゃうぜ。
画像処理100本ノックのうち95本をGo言語で受けてみた

# 結論
[画像処理100本ノックのうち95本をGo言語で書いた](https://github.com/kjmatu/Gasyori100knock)

# やってみた感想
+ OpenCVで実装されている基本的なAPIを自分で実装することで何をやっているかを理解することができた
+ Numpyの行列計算やIndex処理は適切なコメントがないとすぐには意図が読み取れないことが多かった
+ Go言語で行列を計算するのはPython(Numpy)に比べてとても大変
+ Go言語楽しい
+ 95本で止まったのは最後の5問が機械学習との融合問題になっており、機械学習の知識を得てから取り組みたかったので95までしか解いてません。

# 画像処理100本ノックをやった動機
+ 機械学習を勉強するための前準備として画像処理を復習したい。そして画像を使った機械学習アプリケーション作成につなげていきたい。
+ 学生時代にOpenCVのAPIを叩きまくって卒業したが、中身をちゃんと理解してない気持ち悪さをどうにかしたい

# Pythonでやらなかった理由
+ Pythonを普段業務で書いているので違う言語をやってみたかった
+ Python実装が既にあるので、油断するとそれを見て思考停止してしまい自分で考えなくなりそうだった

# Go言語にした理由
+ C言語とPythonを普段の業務で書いていて、Goの評判を聞くとその丁度中間の言語だと感じたのでやってみた
    + いろんな方が言及している通り静的型付言語としての厳格さと動的言語の書きやすさが同居している不思議な感覚で実装できた
+ 標準ライブラリで画像の入出力が可能であり、OpenCVのAPIすら使わずに画像処理プログラムを書くことが可能だと思った
    + 実際にできた

# 反省点
+ Hilditch細線化やCannyEdgeなどの計算結果が微妙にPython実装と違っており、まだ十分に評価できていないので今後改善してく
+ Go言語での基本的な実装に慣れることができたが、Interfaceや構造体を使った実装に取り組むことができなかった
+ 問題文にはアルゴリズムの計算方法までは書いてあるが、どのような背景でこのアルゴリズムが導かれたかまでは言及していないので別途そこは補強していく必要がある。(逆に言うとそういう観点で画像処理のアルゴリズム見れるようになる)

# 注意点
+ 同じ画像でもOpenCVでjpeg画像を読み込んだRGB値とGo言語のImage Packageで読み込んだ値が微妙に違うため全く同じ計算結果にならない。よって、Pythonで生成した画像とGoで生成した画像を比較して目で見て評価を行う場面が多かった。
+ 初期化する際に使用するランダム値がPythonとGo言語だと違うため、自分で実装した計算結果確認のためPythonのランダム値を代入して確認する必要がある

# 最後に
大変良い勉強になりました@yoyoyo_さんに感謝します。
また、同じように100ノックをやっているコントリビューターさんが改善活動をしており、今後より良い画像処理練習問題になっていくと思いますので画像処理に興味があるかたはやってみてはいかかでしょうか。また、Pythonでもnumpyを使わない実装や他の言語での実装もあると様々な比較ができて面白い教材になるかと思います。
Windows 環境の expo-cli で react native をやろうとして環境構築で詰まった箇所

環境構築で丸一日弱使ってしまったので、詰まった箇所を雑多ですが備忘として記載しておきます。
（実行日：2019年04月21日）

## やったこと

・node.js のインストール
・yarn のインストール　→　結局使わず
・expo-cli のインストール
・WSL のインストール
・Genymotion と virtualbox のインストール
・VSCode のインストール（JSコーディング用）
（Android Studio は既に昔にインストール済み）

## エラー１：yarn で expo-cli がインストールできない

```
yarn add global expo-cli
```
で、インストールを実行すると下記のエラーが出ました。

```
info There appears to be trouble with your network connection. Retrying...
```
yarn でこのエラーが出た場合は、 --network-timeout 1000000 をつければいいという記事もあったのですが、これでは解決せず、インストール対象のうち2つがインストールができずでした。

結局これは原因が分からず… npm で下記コマンドでインストールしました。

```
npm install -g expo-cli
```
これも何か Linux 用の何かが足りないというようなエラーが出たのですが、その日は寝て次の日やり直したらインストールできてしまったので、エラーをメモってなく。
WSLを使えるようにしたのが関係してたかもしれませんが、怪しいまま次に進むことに…。

## エラー２：QRコードを実機で読み取っても正しく表示できない

無事 expo-cli でプロジェクトを作成し、起動できるようになったものの、Android アプリの実機にインストールした expo でQRコードを読み込んでも「something went wrong」と表示されてしまうエラーが出ました。

これが出る原因として他記事で多くあげられていたのは、下記のような理由でした。
・スマホの Wi-Fi が同じネットワーク内にない場合
・ファイアウォールでブロックされている場合

が、自分の場合はどちらでもうまくいかず。
原因はexpo の画面の CONNECTION に「Tunnel」「LAN」「Local」と3つの選択肢があるのですが、「LAN」を読み込んでいたことでした。
Tunnel を選択したら、表示されるようになりました。
LAN の IP が virtualbox のゲストOSのIPで、スマホからそのIPにアクセスできなかったのが原因だったため、そこをアクセスできるようにすれば別の方法で解決も可能かもしれません。

## エラー３：Genymotion で端末が起動できない

virtualbox の端末が起動できなかったのですが、これはまんま下記の記事の通りです。
https://ja.stackoverflow.com/questions/47005/virtualbox%E4%B8%8A%E3%81%A7%E4%BB%AE%E6%83%B3%E3%83%9E%E3%82%B7%E3%83%B3%E3%82%92%E8%B5%B7%E5%8B%95%E3%81%97%E3%82%88%E3%81%86%E3%81%A8%E3%81%99%E3%82%8B%E3%81%A8%E3%82%A8%E3%83%A9%E3%83%BC%E3%81%AB%E3%81%AA%E3%82%8B

ネットバンキング用に入っている Rapport のせいでした。いったんアンインストールしたらうまく動きました。

## エラー４：Genymotion で端末起動後、expo がエミュレータで動かない

次のエラーは、ブラウザ上で「Run on Android device/emulator」をクリックした際に出たエラーです。

```
Couldn't start project on Android: could not install *smartsocket* listener: cannot bind to 127.0.0.1:5037: Only one usage of each socket address (protocol/network address/port) is normally permitted. (10048) could not read ok from ADB Server * failed to start daemon * error: cannot connect to daemon
```
Genymotion で Device は起動済みの状態でした。

解決方法は環境変数の PATH に「C:\Program Files\Genymobile\Genymotion\tools」を追加したら直りました。

最初は、
> Genymotion の Settings -> ADB で 「Use Genymotion Android Tools」ではなく、「Use custom Android SDK tools」を選択して、Android Studio の SDK のパスを設定するべき

というような記事を見かけたので、そちらでいろいろ試していたやっていたのですがうまくいかず、最終的に「Use Genymotion Android Tools」の方の設定で、上記のように環境変数を追加したら直りました。

## 完了

以上で、自分の Android 実機と、Genymotion の端末両方で確認できるところまでできました。
ネイティブJavascriptで簡単なバリデーション処理をやってみる

#概要
ネイティブJavascriptで簡単なバリデーション処理を作ってみました。私自身Javascriptは全く分からずだったので、結構手こずりました。でもJavascriptの勉強にはだいぶなりましたよ。フレームワーク使えば瞬殺なんでしょうけど、ネイティブJavascriptわかってない状態でいきなりフレームワークでできました！っていうのは個人的には嫌だったので。。。

#要件
例えば、以下のようなHTMLに対して、Javascriptでバリデーションをかけます。


```HTML:
<form action='/userinfo' method = 'post' id = 'userinfo'>
  <input type = 'email' placeholder = '電子メールアドレス' id = 'email'>
</form>
```
今回は以下のバリデーションパターンとなります。
・文字が入力されているか
・メールアドレスの形式になっているか

#Javascriptコード
以下を参考にしました。
参考サイト
http://blog.tofu-kun.org/070920122122.php
http://makky12.hatenablog.com/entry/2016/08/26/205012

汚いコードですみませんが、成果物は以下です。

```Javascript:
function checkemail(){
  var emailid = document.getElementById('email');
  //xxxxx@yyyy.zzzの形式かどうかをチェック
  var emailreg = /^[A-Za-z0-9]{1}[A-Za-z0-9_.-]*@{1}[A-Za-z0-9_.-]{1,}\.[A-Za-z0-9]{1,}$/;
  //エラーメッセージ表示用divタグのid名の一部に利用する
  var errorid = 'checkmailerror'
  //emailタグの親要素はformであり、これを使いまわすため、変数として定義
  var formid = document.getElementById('userinfo');
  var divtag = document.getElementsByTagName('div');
  //変数erroridの正規表現
  regobj = new RegExp(errorid);
  //同じエラーメッセージが何度も表示されないように
  //前回のエラーメッセージを拾って消去する。
  for(i = 0; i < divtag.length; i++){
    if(divtag[i].id.match(regobj)){
      formid.removeChild(divtag[i]);
    }
  }
  
  //emailのバリデーション
  if(!emailid.value){
    var error = document.createElement('div');
    //メッセージ表示のためのdivタグのidは重複を避けるため
    //erroridと固有の文字列を結合している。
    error.id = errorid + 'notvalue';
    var errormsg = document.createTextNode('メールアドレスが入力されていません');
    error.appendChild(errormsg);
    //上記により<div id = 'checkmailerrornotvalue'>メールアドレスが入力されていません</div>が生成される。
    formid.insertBefore(error,emailid.nextSibling);
  //・メールアドレスの形式で入力されているかどうか
  }else if(!emailid.value.match(emailreg)){
    var error = document.createElement('div');
    error.id = errorid + 'notmatch';
    var errormsg = document.createTextNode('メールアドレスの形式になっていません');
    error.appendChild(errormsg);
    formid.insertBefore(error,emailid.nextSibling);
  }
}
```

DOMちゃんとわかっていればすぐに書けるんですけど、付け焼刃ではなかなか厳しかったですね。
はまっていたのは以下

```Javascript:
formid.insertBefore(error,emailid.nextSibling);
```

当たり前のことですが、テキストボックスがformの中にある場合は親要素がformになります。
親要素がformのemailidに対してhtmlを生成、とする必要があります。私はここを適当にdocument.bodyとかやっていたので（あほ）
少々はまっていました。

あと個人的に気になったのはinsertAfterは存在せず、insertBeforeで代替する必要があるということですね。
詳細は以下
https://developer.mozilla.org/ja/docs/Web/API/Node/insertBefore

#なんでこんなことしてんの？
申し込みフォームをフロントからバックまで一通り実装してみようかなと思ったから。勉強のため。
勉強なのでできる限りフレームワーク使わないで実装中。なお、バックエンドはruby（sinatra）の模様。
AdobeのID取得ページを参考にレイアウトしています。デザインダサいですが、実装を学びたかったのでそこは勘弁。
https://adobe.ly/2IyLwGa
なお、画面含めたクソコードは以下にあります。
https://github.com/gitk47320/applyform
結構コードキレイにしたいけどとりあえず次はバックエンド行きます。バックエンドは余裕で行けるはず・・・
34日目 Rubyのメソッドの使い方

三日坊主にならないように・・・！
今日はProgateでRubyのメソッドの使い方を学びました。

#Ruby Ⅰ 復習
変数、if文、条件式
ほとんど手間取らなくなったけど、何個かひっかかった(12分)

#Ruby Ⅱ 復習
配列、each、if 
ちょっと手間取って(18分)

#Ruby Ⅲ メソッドの使い方

###def-endで囲む
```
def aaa
	puts "aaa"
end 
```
で囲むとその間にかいたプログラムを呼び出せる

###def aaa(name)で引数を渡せる
```
def aaa(name)
	puts "#{name}"
end 

aaa("test")
```

###def aaa(name,price)で複数の引数を渡せる

###returnで戻り値を使う
```
def sum(a,b)
	return a + b
end 
aaa = sum(1,2)
puts aaa
```
### defに条件をつける
こういう使い方でできるって面白い。

```
def aaa?(num)
  return num >= 1000
end

if aaa?(3000)
	puts "1000 over"
else
	puts "1000 under"
end
```
###defの中で条件を使う
returnにかかると以降の処理が行われない。
defの中でifを作って、ifにかかる場合とかからない場合で処理を分ける
好みもありそうだけど、こっちの方が読みやすいかも？

```
def aaa(num)
	if num >= 1000
	  return price
	end

	return num + 500
end
```
###キーワード引数
プログラムのどこに何の引数を渡すかわかりやすくできる。

```
def buy(item:, price:, count:)
	puts "#{item}を#{count}台のお買い上げです"
	puts "合計金額は#{price * count}円です"
end
# キーワード引数を使うように書き換えてください

buy(item:"テレビ", price:15000, count:2)

puts aaa(5000)
```

###完成！
（所要時間45分）