概要
- ShellScriptの書き方
- bashができれば大体shもできるので、bashメイン
- シェル芸の問題と解答を公開しているサイトがある
目次
- 疑問
- 問題集
- DQ, SQ, 何もなしの違い
- parallel
- 使用ケース
- Tips
- 計算
- デバッグ
- bashとshの違い
- 文法
- find
- xargs
- sed
- awk
- make
- backquote
- for文
- セパレータ
- $''
- while
- 文字列の比較
- 何もしない
- if
- test
- grep, egrep
- $?とパイプ
- Gnuplot
- awk
- complete
- Dropbox
- 自動起動
- wget
- cron
- sendmail
- md5sum
- iconv, nkf
- sed
- sort
- jq
- nkf
- cmake
- cron
- byobu
- emacs
- wget
- pkgconfig
- git
- gnuplot
- Qt Creator
- clang
- dd
- pgrep
- kill
- screen
- valgrind
- tmux
- vi
- graphviz
- tar
- cpufreq-set
- chrt
- ifconfig
- zfs
- ab
- 各種設定ファイル
疑問
- echo '432' | awk '$0~"\."'は何で\が二つ必要なの?
- シングルクオートとかバッククオートの中で、\が二つ必要なケースが何個かある。統一的な理解は?
問題集
- 特に指定されなければ、ファイル名はhogeで。
- https://docs.google.com/spreadsheets/d/1I6V8Y_WwI8BCbkDG_l2dGu49Qde-T8aqDjSjKKGgmGY/edit#gid=0
- (wikiの表ではパイプが使えなくてむり)
DQ, SQ, 何もなしの違い
- SQは展開しない、何もなしはスペース区切り始めのものだけ展開、DQは全部展開
A=test
B=$A echo hoge # Bに"test"が入って、hogeが標準出力
B="$A echo hoge" # Bに"test echo hoge"が入る
B='$A echo hoge' # Bに"$A echo hoge"が入る
parallel
time seq 1000 | parallel -j 1 ./a.out | sort -n
3.6s
time seq 1000 | parallel -j 8 ./a.out | sort -n
1.3s
time seq 1000 | parallel ./a.out | sort -n #指定しないとコア数分並列化
1.3s
- timeはパイプ全体の時間計測する
使用ケース
- ファイル並列
ls orig/* | parallel -j 10 "echo < {} > {}.log"
- 行並列
cat big_size.txt | parallel --pipe -L 10000 "awk '{n+=$1}END{print n}'" > compressed
- グリッドサーチ
lr=(0 0.05 0.10)
units=(100 200 300)
parallel "./a.out {1} {2} > {1}_{2}.log" \
::: ${lr[@]} ::: ${units[@]}
- 入出力ファイルがある場合
seq 10 | parallel bash -c "./game < sample1 > output{}"
# -a - でパイプから入力を受け取る
$ ls * | parallel -a - --dry-run echo
echo a
echo b
# {} で場所を指定できる
$ ls * | parallel -a - --dry-run echo {} end
echo a end
echo b end
# アトミックな処理をしたいなら '' で囲む。というか基本的には囲んだほうがいい
$ ls * | parallel -a - --dry-run 'echo {} 1; echo {} 2'
echo a 1; echo a 2
echo b 1; echo b 2
echo test.xt 1; echo test.xt 2
echo x.txt 1; echo x.txt 2
# {.} で basename が取れる。test.sh なら test
$ echo test.sh | parallel -a - --dry-run echo {.}
sh -c echo test
# zip の例
$ ls *.zip | parallel -a - --dry-run 'mkdir {.}; unzip {} -d {.}; rm {}'
Tips
- McIloyによるパイプの発明により、部品に分解
- 部品の組み合わせは指数関数的に存在するので、大きなコマンドを作るより適用性が高い
- Shell Scriptの文法が汚いのはしょうがない
- 「手のように」使える必要があるので、文法的に汚いが、じゃあC++みたいに複雑にする?という話がある
- R.Pike データ構造がアルゴリズムを規定する。"Representation is the essence of programming (Brook)"
- プログラムのほとんどは例外処理
- sudo apt-get install manpages-jaを入れると日本語のmanが手に入る
- treeというコマンドでディレクトリ構造を木構造として描画してくれる。
- POSIX
- UNIX互換OSにはさまざまな機能の追加や変更がなされているため、UNIX互換OSの間で最低限必要な仕様や規格を定め、互換性を保つため
- 全UNIXで動く本、みたいなものを書こうとしたら、これに準拠する必要がある
- でも拡張を模索し、良いユーザたるには、それは関係ないよね?
計算
VAR_LEFT=5
VAR_RIGHT=5
echo $(($VAR_LEFT + $VAR_RIGHT))
echo $(($VAR_LEFT - $VAR_RIGHT))
echo $(($VAR_LEFT * $VAR_RIGHT))
echo $(($VAR_LEFT / $VAR_RIGHT))
echo $(($VAR_LEFT % $VAR_RIGHT))
デバッグ
- 下らないミスをなくすために、必ず以下をかくこと
#!/bin/bash
- コマンド展開
sh -x test_eval_1.sh #展開後実際に起きていることがわかる
bashとshの違い
- リダイレクト先にメタ記号を使えない
文法
if
if [ $? -eq 1 ] # []の回りにスペース必須
then
continue
fi
for
- for文ではcontinue可能
終了ステータス
- $?で終了ステータス
- grepで見つかったかどうかなどが分かる
配列
list=("1332" "1333" "1605") # =の間にスペースを入れると死ぬ
include
. list #listは実行可能である必要は無い
find
find .
find . -type f
find . -type ! -name "*~"
find . -type f -a \( -name "*.c" -o -name "*.h" \)
- なぜかfind . -type ! -name *~は動作しない。
- hoge*, "hoge*", 'hoge*'の違いが知りたい
- $"とかもあるの?"
xargs
ls -1 | xargs echo
find . -print0 | xargs -0 echo
find . -print0 | xargs -0 -L1 echo
find . -print0 | xargs -0 -L2 echo
find . -print0 | xargs -0 -I{} echo "<{}>"
- findからxargsにパイプする場合は、絶対findの-print0をいれてxargsに-0を入れる。
ls | sed -e "p;s/\.jpeg$/\.jpg/" | xargs -n2 mv
for i in *.jpeg ; do mv $i `basename $i .jpeg`.jpg ; done
-
頑張ってmv, cpなどの二つ同じものが出てくる場合は、このようにsedの;セパレータと-n2で頑張る
- sifiたんありがとうございます。
-
cat ~/tmp/questions_to_check | xargs -P 100 -n 1 tct questions resolve > ~/tmp/path
- 並列コマンド実行で便利なやつ
sed
- オプション-Eで拡張正規表現も使える。
sed -e 's/#//'
- Hitしなければそのまま表示、Hitすれば処理をして表示
sed -n 's/#//'
- Hitしてもしなくても非表示
sed -n 's/#//p'
- Hitすれば処理をして表示
- そもそもHitしているか、何回Hitしているかを確認するために、-eにpをつけることもある。
echo 'a a' | sed -e 's/ *//'
- 出力は"a a"
- なぜなら、1つ目のaの前にマッチするから。
sed -e '1s/rep/p/'
-
1行目のrepをpに変換
- 行数の指定は一番初めに書く。指定方法は
- 1: 1行目
- 1,10: 1行目から10行目
- 1,+10: 1行目から11行目
- ^,$: 行頭から行末まで
- など
- 行数の指定は一番初めに書く。指定方法は
-
sedは{とか}をエスケープ必要がある
- でもgrepはそうでもない
- どういうのがエスケープ必要で、必要ないの?
- Sedは1行でマッチする文字が何通りもある場合は、一番長いものにマッチする。(sed ‘[l],[r]s/<[^<]*>//’の時、前半はオンオフで制御され、後半はきちんと最長一致で制御されている。)
awk
- awkで置換
echo "replot" | awk '{sub(/^rep/, "p", $0); print $0}'
make
Makefileの$のエスケープは$$
backquote
echo hamu
echo `echo hamu`
echo `echo \`echo hamu\``
echo `echo \`echo \\\`echo hamu \\\`\``
for文
for var in `echo "a b"`
do
echo ${var}
done
for var in `echo "a b"` ; do echo ${var} ; done
- 1行の場合は、doの後に;を入れてはならない
- 1行にする場合は二つ目のechoの後の;が必須。ないとechoがdoneを食ってしまう。
セパレータ
#!/bin/bash IFS=' \t\n'で echo $i done
$''
中の\t, \b, \nなどを展開する。~ これはalt-v [tab], alt-v [backspace], alt-v [enter]に相当する。~
echo "a\na"
\n
echo $'a\na'
a
a
while
while read i;do echo $i;done < file
- 1行の場合は、doの後に;を入れてはならない
文字列の比較
{var} != "A"
- if [ ${var} = A ]と何が違うの?違わないとしたら""の意味は何?
何もしない
:
if
- 中のコマンド実行結果が0ならthenを実行する構文。
if command
then
expression
fi
if command ; then echo a ; fi
- 空文字列判定
if [ -z "${opts}" ]; then
echo "null stream"
else
echo "not null stream"
fi
- 空ファイル判定
if [ -s test.txt ]; then
echo "exist"
else
echo "not exist"
fi
- ダブルクオーテーションで囲まないとだめ
test
- testと[は同じ意味。
if [ condition ]
then
expression
fi
if [ -e hoge ] ; then echo a ; fi
- 一行の時はthenの後に改行を入れてはならない。
grep, egrep
- egrepはgrepの正規表現が新しいバージョン。+, ?が使える。~
- 実行結果は、検索に引っかかったら0, 引っかからなかったら1
echo $' \t' | grep $'^[ \t]+$' ; echo $?
1
echo $' \t' | egrep $'^[ \t]+$' ; echo $?
0
- ちなみに-Eをつけるとegrepと同じ動作に
- これはsedでも同じ挙動をする
echo $' \t' | grep -E $'^[ \t]+$' ; echo $?
1
$?とパイプ
echo "hoge" | grep "test" | echo $?
- 出力をechoが食おうとしているから、grepの終了コード1を正常に取得できない。
echo "test" | grep "test" ; echo $?
- grepが終わってからechoしているので、1が表示される
Gnuplot
式
plot "file" u 1
plot "file" u ($1)
- uの後は、カッコでくくると式モードになって、1などは$1などにしなければいけなくなる。
for
- a
1 2 3
2 3 2
3 5 2
5 8 1
plot for [i=1:3] "a" u i
sprintf
plot for [i=1:3] sprintf("hoge%02d", i) t sprintf("hoge%02d", i)
- hoge01, hoge02, ...をplot
system
- num.config
3
num = system("cat num.config")
plot for [i=1:num] sprintf("hoge%02d", i) t sprintf("hoge%02d", i)
数字と文字列の連結
n = system("awk '{print NF; exit}' motenc_state")
replot for [i=2:n] "dv_motor" u i title "Motenc State".(i-1)." [unknown]"
awk
1行目のフィールド数の取得
awk '{print NF; exit}' file
complete
complete
complete -o dirnames -f -X '!*.mp3' mp3nantoka.sh
- COMPREPLYの中を候補に表示する「だけ」
comptest2 () {
COMPREPLY=( aaa bbb )
}
complete -F comptest2 hoge
hoge [tab][tab]
comgen
- aaa, bbbを候補に表示し、補完
comptest1 () {
COMPREPLY=( `compgen -W "aaa bbb" $2` )
}
complete -F comptest1 hoge
hoge [tab][tab]
定石
function _hoge {
local arg opts
COMPREPLY=()
arg="${COMP_WORDS[COMP_CWORD]}"
opts="`ls -1`"
IFS=$'\n'
COMPREPLY=($(compgen -W "${opts}" -- ${arg}))
unset IFS
}
complete -F "_hoge" "hoge"
Directoryのパスの場合
complete -F "_plotter" -o "nospace" "plotter"
- nospaceのoptionをつけると、最後にスペースが入らなくて良い
Dropbox
~/.dropbox-dist/dropboxd
自動起動
Startup Aplicationからクリックで頑張る
wget
- URLのソースコードを取得する
wget https://twitter.com/
cron
- cronの設定を行う。書式はググる。
crontab -e
crontab -l
- 例
- cron_has_calledはデフォルトでhomeに出力されるようになっている。
23 * * * * echo "hallo" >> cron_has_called
echo "test" | mail wakataberyo@gmail.com
sendmail
- headerを明示的に書く必要があるのと、mailに比べて愚直である。
- headerの例(最後は改行が必要)
Content-Type: text/plain; charset=iso-2022-jp
Subject: test
- 使い方
cat header honbun | sendmail wakataberyo@gmail.com
md5sum
- 文字列をハッシュにする。
echo "test" | md5sum
d8e8fca2dc0f896fd7cb4cb0031ba249 -
- ハイフンには標準入力という意味がある。
iconv, nkf
- 文字コード変換
- iconv
- 文字コードをFROMからTOにする。
- 半角カナ文字が入っていると対応できないので、日本語を扱うときには基本的にnkfを使う。
iconv -f FROM -t TO
- nkf
- 文字コードをguessしてISO-2022-jpにする
cat file | nkf -j
- 文字コードをguessしてSHIFT-JISにする
cat file | nkf -s
sed
- 特定の正規表現のワードを取り出したい時
- -n, /pを使うのと、^から$までを全部ヒットさせるのがコツ
cat $i | sed -n 's/^.*`\(.*\)`のクラス.*$/\1/p';
- 正規表現にヒットした行のみ正規表現で置換

ITP1_2_D

ITP1_8_D
$ cat test | sed -E '/^ITP/s/ITP/hoge/g'

hoge1_2_D

hoge1_8_D
'のエスケープ
- 'は、'''でエスケープできる。
- 何をやっているかと言うと文字列の concat をしている。sed のコマンドを一回切って、'を挿入している。
- 例: echo 'test''abcd' -> testabcd が出力される
a
ChatCompletionMessage(content='excel', role='assistant', function_call=None, tool_calls=None)
コマンド
$ cat a | sed -n 's/^.*content='\''\(.*\)'\'', role.*$/\1/p'
excel
sort
- ソートする列を指定
sort -k 2 input_file
- 数値としてソート
sort -n input_file
jq
nkf
- 文字コード確認
nkf -g readme.txt
- UTF8にする
nkf -w --overwrite *
cmake
cron
- crontabの実行パスは/
- ./run.shを実行するためには以下のようにする
MINUTELY_PATH=/home/ryo/git/stocks/utils/minutely_sh
16 19 * * * cd $MINUTELY_PATH; ./run.sh
byobu
-
分割可能なターミナル
- Ubuntuみたいなalt-tabの効かないクソUIのお供
-
実際にはscreenのラッパ
-
参考
-
セッション
- 複数画面をつくることに相当
-
使い方
- Shift+F2(C-a S)で縦分割,Shift+F4(C-a Tab)で分割間移動
- F2(C-a c)でウィンドウ作成,F4でウィンドウ間移動(C-a n/p),セッション番号を指定して切り替え(C-a 数字)
- C-a kで現在のカーソルのセッションをkill
- F6でデタッチ
-
例
- byobuを立ち上げる
- 以下の1s.cをつくる
#include <stdio.h>
main(){
int i = 0;
while (1) {
i++;
printf("%d\n", i);
sleep(1);
}
}
- gcc 1s.c
- ./a.out
- F6
- 1分たったあたりでbyobuを再度起動=アタッチ
- バックグラウンドで./a.outが走っていたことがわかる
emacs
チートシート
- 終了とかファイル開くとかウィンドウみたいな、メタなやつは大概C-x
| Vim | Emacs | 備考 |
|---|---|---|
| :qa | C-x C-c | 全終了 |
| :sp, :vsp, C-w w, :q | C-x 2, C-x 3, C-x o, C-x 0 | C-x 0がウィンドウ削除 |
| :e, :w, :w filename, :q! | C-x C-f, C-x C-s, C-x C-w, C-x k | ファイル開く・保存・別名保存・強制終了 |
| kjlh | C-pnfb | |
| 0$ | ae | |
| x | C-d | |
| dd | C-a C-k | |
| u, C-r | C-/, C-g C-/ | C-gすると、undo-redoが入れ替わる仕様 |
| J | C-e C-k | 行をマージ |
| / | C-s, C-r | 検索。二回以上遷移したい場合はC-sを何回も押す。行き過ぎたらC-r |
| y | C-y | |
| 100dd | C-u 100 C-k | C-u 100みたいな感じで何回もというのを表す |
| O | C-o | 上の行を作る |
自動補完
- M-x list-packages
- M-x company
インストール
- 25.1じゃないといろいろダメ
- Anacondaをインストール
- https://twitter.com/hamko_intel/status/925153140080508928
$ cd /tmp
$ wget -O- http://ftp.gnu.org/gnu/emacs/emacs-25.1.tar.xz | tar xJvf -
$ cd emacs-25.1
$ sudo apt install libgtk-3-dev libwebkitgtk-3.0-dev libgif-dev Inconsolata
$ ./configure --disable-largefile --with-x-toolkit=gtk3 \
--without-toolkit-scroll-bars --without-xaw3d --without-xim
--without-compress-install --with-sound=no --without-pop
--without-xpm --without-tiff --without-rsvg --without-gconf
--without-gsettings --without-selinux --without-gpm
--without-makeinfo --with-x --with-modules --with-xwidgets && time make
$ sudo make install
- どのパッケージをインストールすればよいかわからない場合、以下のコマンドをうつと似たようなものが表示されてくれる
apt-cache search mysql-server
wget
- wgetで認証付きのサイトを回る
- https://qiita.com/hirohiro77/items/b774908436ec032df719
- セッションクッキーとかhttp://webos-goodies.jp/archives/51277893.html
- 通常まともなサイトではセッションクッキーを使っている
- DevTool>Network>index.html>Headeres>Request Headersを設定するとちゃんとwgetでもできるようになる。具体的には、 wget --header 'Cookie: %s' http://webos-goodies.jp/index.html
- CentOSでメールを送るコマンド
echo "本文" | mail -s "タイトル" hogehoge@gmail.com
- 添付ファイルはhttps://inexio.jp/20150225-610 参照
pkgconfig
- 設定方法:/usr/local/lib/pkgconfig/coolVisi.pc として,
# coolVisi Package Information for pkg-config
prefix=/usr/local/isi
exec_prefix=/usr/local/isi
libdir=/usr/local/isi/lib
includedir=/usr/local/isi/include/coolVisi-2.0
Name: libcoolVisi
Description: ISI statistics and image processing library
Version:2.0.0
Libs: -L/usr/lib/x86_64-linux-gnu/octave/3.8.1 -loctave -lcruft -lreadline -L/usr/local/isi/lib -lcoolVisi -ljpeg
CFlags: -I/usr/include/octave-3.8.1 -I/usr/local/isi/include/coolVisi-2.0
git
- git book読め
トラブルシューティング
- 日本語が文字化けする→以下を打つだけでOK
git config --local core.quotepath false
- タグ'tagname"を作る
git tag tagname
- タグ"tagname"を削除
git tag -d tagname
- リモートタグ"tagname"を削除
git push origin :TAGNAME
- pushしていないタグを全てpush
git push origin --tags
- ブランチの可視化ツール
gitk
- でっかいファイルを間違えてコミットしてしまったら
git filter-branch --force --index-filter 'git rm --cached --ignore-unmatch でかいファイル.tar.gz' --prune-empty --tag-name-filter cat -- --all
git commit --amend -CHEAD
git push
運用
-
段階的マージ
- masterは本番環境おで動いているコードと透過
- verX.X-pr ステージング、バージョン開発ごとの新機能のまとまり
- verX.X-deploy 試験用サーバ 開発者が好きにプッシュして遊ぶ場所。CI通ってなかったりもする
- プルリクをverX.X-prから切る→開発(実機確認では-deployにマージ)→CIとレビューが通るとprにマージされる→深夜メンテナンスで-prがmasterにマージされる
- レビュアーは10人くらいいる可能性があるなど、非常に厳しいレビュー
-
コミットごとのレビューか、プルリクごとのマージか?
- 普通はプルリクごと
- コミットごとにレビューになる場合、人ごとに変更をまとめる必要があり、squashを求めるケースがある
逆引き
- rebaseのrewordという機能はコミットメッセージだけ変えることができる
- squashはsで代替できる
- git merge-baseで共通祖先が見つかる
- コンフリクト中には、conflictを解決するか、git merge --abortのどちらかしか選択肢がない。
理解すべきこと
- fast-forwardマージとは?
- rebaseとは?
- git rebase -i $(git reb-list HEAD | tail -n 1)
- force pushとは?何が起きるのか?
gnuplot
- Gnuplotの仕様上の欠陥とバグをすり抜けて、目的の動作をさせる方法
eps(論文用)
set xrange [0:400]
p "bla" u 1:4 w l
rep "eigen" u 1:4 w l
set terminal postscript eps enhanced color
set output "out.eps"
replot
png
set xrange [0:400]
p "bla" u 1:4 w l
rep "eigen" u 1:4 w l
set terminal png
set output 'sinc.png'
点を打つ
set label 1 point pt 7 ps 3 lc rgb "dark-violet" at 0,0,800
ヒートマップ
set pm3d
set pm3d map
set ticslevel 0
set cbrange[-1:1]
set palette defined (-1 "blue", 0 "white", 1 "red")
splot "data" with pm3d
- dataは以下のような形式になっている必要がある。
1 1 0.33
1 2 0.457
1 3 0.45
2 1 0.33
2 2 0.457
2 3 0.45
3 1 0.33
3 2 0.457
3 3 0.45
gnuplot自動化
バッチモードとインタラクティブモード
-
ttyデバイスが標準入力に割り当てられているときはインタラクティブモード、そうでない場合はインタラクティブモードで起動する。
-
シェルを起動してgnuplotと打つとキーボードがあるのでインタラクティブモード、パイプやなどで流し込むとバッチモードで起動する。
-
外部から起動する場合は↓のようにする(そうしないと一瞬で終了する)。pause -1はバグバグしいので使ってはならない
gnuplot -persist < file
gnuplot -persist << EOF
p 'a.txt'
EOF
共通ファイル
- a.txt
1
2
3
4
5
- b.txt
6
7
8
9
10
コマンド群のバッチ実行
- gnuplot test.gplとしても、gnuplot test.gplとしても、test.gplのEOFを検知した時点でgnuplotは終了する。
- 我々が観測できるのは「gnuplotを起動して描画が終わった瞬間に終了して全くグラフが見えない」という状態。これを防ぐために-persistが必要。
- pause -1は、「インタラクティブモードの時はそこで処理を止め、バッチモードの時はスルーする」という謎コマンド。
- めんどいので使ってはならない。
ファイルによる実行(リダイレクト)
- test.gpl
plot 'a.txt' u 1
- 起動
gnuplot -persist < test.gpl #リダイレクトをしないファイルによる実行は不可!
EOFによる実行
gnuplot -persist << EOF
plot 'a.txt' u 1
EOF
描画すべきファイル名をシェルスクリプトの引数で指定する
- プロットするファイルを変えたい場合はsedなり何なりで、ファイルを作ってからでないとプロットできない。
シェルスクリプトに全部突っ込む
- test.sh
gnuplot -persist EOF
plot '$1' u 1
EOF
- 起動方法
./test.sh a.txt
./test.sh b.txt
sedで置換
- test.gpl.templete
plot 'FILENAMETOCHANGE' u 1
- test.sh
sed 's/FILENAMETOCHANGE/$1/g' test.gpl
gnuplot -persist test.gpl
- 起動方法
./test.sh a.txt
./test.sh b.txt
複数グラフ表示
-
gnuplotで一度に複数のグラフを表示し、その全てに関してマウスからの操作ができるようにしたい。
-
set termで複数の表示しても、その全てでインタラクティブな操作ができるようにするには、仮想ターミナルを作るしかない。xtermをバックグラウンドで起動することで実現できる。
-
plot_a.gpl
plot 'a.txt' u 1
- plot_b.gpl
plot 'b.txt' u 1
- plot_multi.sh
xterm -e gnuplot -persist plot_a.gpl
xterm -e gnuplot -persist plot_b.gpl
- 起動方法
./plot_multi.sh
Cからgnuplot操作
- パイプでつなげるだけ。
#include <stdio.h>
int main(void)
{
FILE *gp = popen('gnuplot -persist', 'w');
fprintf(gp, 'set parametric\n');
fprintf(gp, 'set size square\n');
fprintf(gp, 'set xrange [-1:1]\n');
fprintf(gp, 'set yrange [-1:1]\n');
fprintf(gp, 'plot [0:2*pi] cos(t),sin(t)\n');
pclose(gp);
return 0;
}
最小二乗法
二次方程式
- ノイズありのy=xxのデータに、y=0.5xx+0x+0を初期値として最適化
seq 10 | awk '{printf("%d %f\n", $0, $0 * $0 + rand());}' > data
cat data
gnuplot
f(x)=a*x*x+b*x+c
a=0.5;b=0;c=0;
plot f(x), 'data' using 1:2 # not fitted yet
fit f(x) 'data' u 1:2 via a,b,c
plot f(x), 'data' using 1:2 # fitted!
指数関数
- モータがエンコーダ速度0から飽和まで加速した場合
f(x)=a*(1-exp(-b*x)) # ''x=0での傾きはab、x=infでの速度はa、bは系に固有''
a=20.0;b=2.0;
fit f(x) './0.6-5step-vel' u ($0/40):1 via a,b # /40は、25ms周期のサンプリングだから
plot f(x), './0.6-5step-vel' using ($0/40):1
多変数関数
- ファイルaの1列目2列目がx, yで、3列目がg(x, y)であるようなデータが与えられた時、以下のようにすれば多変数関数の最小二乗法ができる
g(x,y)=a*x+b*y+c+d*x*y+e*x*x+f*y*y
fit g(x,y) 'a' using 1:2:3:(1) via a,b,c,d,e,f
sp g(x, y)
rep 'a'
plotの中にコマンドを突っ込む
- plot "<command"とすると、plotするデータ群を選択したり、ファイルを連結したりできる。
- plot '<command'では動かない。
- "<"内部に“ダブルクオーテーションは使えない??エスケープする方法がわからない。
plot "<awk '$7 > 2.2049*$5-210.4416 {print}' mani" u 5:8
plot "<paste file1 file2 | awk '$1 > 2.0 {print}'
multiplot
set multiplot layout 2,1 #multiplotの開始、縦2横1自動配置
set xrange [1950:2150]
set yrange [500:1500]
p "a" u 2 w l
set yrange [-1.1:1.1]
p "a" u 3 w l
multiplotでreplot
- replotコマンドは使えない.(参考)
Qt Creator
Shortcuts
- https://www.kdab.com/wp-content/uploads/stories/qtcreator-card2.pdf
- settings: Tools > Options > Environment > Keyboard
| F2, Ctrl-Click | Follow Move to definition |
| Ctrl-Shift-U | Grep all occurence |
| Ctrl-b | build |
-
Vim mode
- qtscreen->advanced edit->vim editing
-
Vertical split
- If vim mode is enable, the following is enough
:vsp
clang
- エラーメッセージが親切でコンパイルが早いC++コンパイラ
- LLVMと関係があるらしい
実例
Chrome 38からGCC 4.6に代わりClangが採用されるようになったのだが、この理由についてPhoronixが記事にしている。 これによると、Clang採用の理由はすでに多くの開発者がLinux上でClangを使っていたということと、C++のより新しい機能を利用するためらしい。Clangは診断出力が優れており、スピードも速く、さらにChromium(Chromeの開発版)に特化したClang向けプラグインも作られていたため、開発者のClangへの移行が進んでいたそうだ。GCCのより新しいバージョンではC++の新機能のサポートが進んでいるものの、GCCをアップグレードするよりもClangに移行したほうが容易だと判断したという。 実際にClangに移行したところ、性能面ではほとんど変化はなかったが、バイナリサイズは8%ほど小さくなった
- http://yohshiy.blog.fc2.com/blog-entry-294.html
- -Wdeprecated-registerの対応は,-Wno-deprecated-register
dd
- imgをSDカードに書き込み
sudo fdisk -l # SDカードに相当する/dev/sdXを調べる
cat /proc/partition # SDカードに相当する/dev/sdXを調べる方法その2
# bs=10Mとかしておくと高速化される
dd if=~/sdcard_backup.img of=/dev/sdX bs=10M status=progress
-
cat /proc/partitions
- sdbとかsdaとかのサイズ
- 論理的に区切られていたりとかしたら、BeagleBoneのReadmeと実際のイメージが異なるみたいな感じで、1つのsdカードがsdb、そのなかの論理的なパーティションがsdb1, sdb2みたいになっている
-
シグナルを送ると現在の進行状況を出力するような機能がある.man ddをみるとSending a USR1 signal to a running 'dd' process makes it print I/O statistics to standard error and then resume copyingと書いてある。sudo kill -USR1 $(pgrep ^dd)とすると、dd側のターミナルでどれくらいのサイズ書き込まれたかが表示される
- 現在の進行状況を出力しながらやるというコマンドもある
- pvコマンド
- ddのifとofの間に突っ込むと何故か進行状況が出力される
- 現在の進行状況を出力しながらやるというコマンドもある
pgrep
- プロセスを正規表現で探すことができる
- ddコマンドのプロセスidを探すときに、ps|grepうにょうにょすることなくでよい。
pgrep ^dd
kill
- killコマンドは、プロセスにシグナルを送ることもできる。シグナルにはUSR1などのコマンドがある。名前がおっかないね。
kill -USR1 $(pgrep ^dd)
screen
- C-aでコマンドモード
- 閉じる:C-k
- screen -r mcs -X stuff '/save-all\n/save-off\n'
- 動作中の screen セッションに特定のコマンドを送る。
- d や -r オプションを用いれば、 アタッチされているセッションやデタッチされているセッション のみを探すよう、screen に伝えることもできる。
- ただしこのコマンドは、 セッションがパスワードで保護されている場合には動作しないことに注意。
- 動作中の screen セッションに特定のコマンドを送る。
valgrind
- 動的メモリチェッカ
参考
- valgrindのFAQ日本語訳
- valgrindの違う使い方
- mtrace(mtraceの便利なところは、ソース内でどこからどこの間でリークを調べたいかを指定できる点です)
- http://blogs.itmedia.co.jp/komata/2009/10/mtrace-valgrind.html
- valgrindはfull, memory_checkで何倍くらい遅いの??
基本的な使い方
-
コマンド
- ふつう
- valgrind ./memleak
- フルオプション
- valgrind --leak-check=full --leak-resolution=high --show-reachable=yes ./memleak
- ふつう
-
見方
- "definitely lost"::
- メモリリークしてるから, とにかく直せ!
- "indirectly lost"::
- ポインタベースの構造 (ツリーやリストなど) があったとき, そのルートノードが開放されていない ("definitely lost") 場合, 子ノードは全て "indirectly lost" となる. ルートノードなどの**"definitely lost" を修正すれば, この "indirectly lost" も消える.**
- "possibly lost"::
- ポインタをうまいこといじくり回さない限り, メモリリークしてしまう.だいたいメモリリークしてる
- "still reachable"::
- おそらく問題無し. 開放すべきメモリを開放していない部分はあるが, これはごく一般的で利にかなっている. この警告を表示したくない場合 --show-reachable=yes のオプションはつけないこと.
- "definitely lost"::
-
よくみるやつ
- Conditional jump or move depends on uninitialised value(s)
- 未初期化の変数を使った。
- これを直すと、突然変な値になる再現性のないバグを防げる。
- Invalid read/write
- 配列外参照。
- これを直すと突然落ちたり、突然変な値になる再現性のないバグを防げる。
- Conditional jump or move depends on uninitialised value(s)
使いどころ
- メモリリークが以下のような状況で起こった場合、問題は特に深刻になる。
- プログラムが長期間動き続けるとき。サーバーサイドアプリケーションや組み込みシステムは年単位で稼働し続けることもある。
- 共有メモリのような、確保したまま終了することが許されるメモリ領域をプログラムが使っているとき。
- ゲームや動画を扱うプログラムのように、メモリの確保・解放を頻繁に行うとき。
- OSやシステムそのものがメモリリークを起こすとき。
- 組み込みシステムやポータブル機のように、メモリの絶対量が少ないとき。
- AmigaOSのように、プロセスが終了してもメモリが自動的に解放されないOSを利用しているとき。メモリリークから回復する手段は再起動しかない。
まとまってないもの
-
Helgrind,マルチスレッドのvalgrind
-
Valgrindの超いい解説.配列外参照なのに検出されないところの解説もある
tmux
- 軽いterminator
- サーバサイドで起動して、shellを切っても残ってくれるので良い
コマンド
- tmux a # tmuxが既にあれば入る
- tmux # tmuxを1つ新しく作る
- c-b c # ウィンドウを作る
- c-b n, p, 0, 1, 2 # 次、前、0, 1, 2のウィンドウに移動
- c-b d # tmuxから一旦出る
- c-b % # 左右にペイン分割
- c-b " # 上下にペイン分割
- c-b o # ペイン移動
vi
- vim、自分が把握できる範囲のコードを書く分には本当に早い。
メモ
vimのタブ系のコマンド.http://qiita.com/tekkoc/items/98adcadfa4bdc8b5a6ca
noremapは,「vimの標準のものにマップする」という意味http://cocopon.me/blog/?p=3871
Vimの分割を平均的にする :new :q
Vimの便利コマンドは検索したほうがいいかも.MとかHとか
q
- シーケンスの保存
- qq[commands]@q
NeoBundle
- 引用
- インストール
mkdir -p ~.vim/bundle
git clone https://github.com/Shougo/neobundle.vim ~/.vim/bundle/neobundle.vim
- .vimrcに以下を追記
"---------------------------
" Start Neobundle Settings.
"---------------------------
" bundleで管理するディレクトリを指定
set runtimepath+=~/.vim/bundle/neobundle.vim/
" Required:
call neobundle#begin(expand('~/.vim/bundle/'))
" neobundle自体をneobundleで管理
NeoBundleFetch 'Shougo/neobundle.vim'
" 今後このあたりに追加のプラグインをどんどん書いて行きます!!"
" 例
" NERDTreeを設定
NeoBundle 'scrooloose/nerdtree'
call neobundle#end()
" Required:
filetype plugin indent on
" 未インストールのプラグインがある場合、インストールするかどうかを尋ねてくれるようにする設定
" 毎回聞かれると邪魔な場合もあるので、この設定は任意です。
NeoBundleCheck
"-------------------------
" End Neobundle Settings.
"-------------------------
- viを開いて閉じてまた開く
vimsnippet
- チュートリアル
vi a.cpp[enter]
for[tab]int[tab]i[tab]0[tab]10[tab]cout<<i<<endl;[esc]
- 設定ファイル
- ~/.vim/bundle/neosnippet-snippets/neosnippet/cpp.snip
- cppのsnippet予約語
- if, for, lambda, p(cout), inc, inc2, static_cast類, helloworld, template, class, class-without-constructor
graphviz
-
グラフを描画するツール
- 二分探索木とかもいける
-
- gveditはdotファイルの作成、編集およびグラフのプレビューを行うことができるGUIのツールです。
-
graphviz+TeX
tar
- 並列tar圧縮
sudo apt-get install pbzip2
tar cvf [圧縮後のファイル名] --use-compress-prog=pbzip2 [圧縮するディレクトリ]
cpufreq-set
- CPUの動的消費電力調整を消す
cpufreq-set --min 500MHz --max 500MHz --governor performance
chrt
- スケジューリングのモードを変える
chrt -f 99 ./a.out
ifconfig
- 以下のような感じでIPアドレスなどを調べることができる
ifconfig
ifconfig eth0
zfs
ファイルシステムのスナップショット
ab
- 一般にストレステストをするためのコマンド
各種設定ファイル
- カーネルパラメータ
/etc/sysctl.d# vi 99-sysctl.conf
vi /etc/sysctl.conf
- /proc/cpuinfo
- /proc/meminfo
- /proc/partition