DOT NOTES

Twitter:@dot_not_ GitHub:@ogrew

0922 団地。

f:id:taiga006:20190921171418j:plain

「有名人じゃなくてもさ、

悪気なんてなくてもさ、

普段の会話の延長線上にあるうかつな発言で炎上する人多いからお互い気をつけたいね」

と言われた。

「たしかに。」

と返事をした。

そういえば最近身の回りで炎上をして傷つけたり傷ついたりする人をみたばかりだった。

「うかつな発言で炎上する人多いからお互い気をつけたい」という緊張状態はもう6,7年ほどずっと続いている気がする。

火に慣れてしまって全部ただのボヤ騒ぎとしか認知できなくなっているのかもしれない。

それはそれで怖いことだ。


炎上した記事や発言、ツイートなどへのコメント欄、リプライを見ていると思い出す景色がある。

小学校に入るまで、僕は団地暮らしだった。

特に変哲もない田舎の集合団地。僕の家は大通りに面した1階の角部屋だった。

その団地は面白い形をしていて、1階の住居と2階の住居の庭が吹き抜けでつながっていた。

そのおかげで1階に住む我が家にも家の奥まで陽の光が差し込んだ。

あるとき、2階の家に住む悪ガキ兄弟が買ったばかりの大きな水鉄砲で吹き抜けの庭から1階の我が家に打ち込んできたのだ。

今考えたら雨と大差ないのだが、晴れの日の我が家の窓をびしょびしょに濡らす奴らがひどく許せなかった。

父が窓から声をかけてみたが、案の定水鉄砲の的にされて終わった。

それはそれで愉快だったが、情けなくもあった。

「放っておけばいいでしょう。」

母の意見にしぶしぶ頷くかたちで僕らは黙って窓の外を見ていた。

その日の夕方、悪ガキ兄弟とその父と思しき人物が家に謝りに来た。

どうして、あんなことしたんだ?と父が聞くと

「1階の庭の草花のせいでうちまで虫が飛んで来るんだ!その退治をしたかったんだ!」

と言った。

「なるほどねー」と父は許したようだったが、僕は納得いかなかった。

悪ガキ二人は誕生日か何かで買ってもらったあの二段式の水鉄砲でとにかく遊んでみた買っただけなんだ、きっと。

でもわざわざそれを口に出す気にはならなかった。

正当化する用意をしてから打つ。ただ、ただ。

反撃されない、平和な位置から、一方的に。


別に世間の炎上案件にあーだこーだ講釈を垂れるつもりもないし、この昔話と無理やりリンクさせるつもりもないけれど、僕は世間の炎上ネタを見るとあの時の景色を思い出す。

「反撃されない、平和な位置から、一方的に。」

それが水鉄砲だったら、別にいいのだけれど。

marshmallow-qa.com

0921 口内炎。

f:id:taiga006:20190921180659j:plain

話題の「彼方のアストラ」を見終わった。まさにSF版「SKET DANCE」だった、最高だった。

ありがとう、篠原先生。 ありがとう、Amazon Prime Video。

久しぶりにSKET DANCEを読もうとして本棚を見渡したが、見つからない。

そういえばこの家に引っ越すとき、

(そう大学院を辞めて仙台から横浜に引っ越してきたとき、)

漫画の量がとてつもなくて半分ほど実家に送ってしまったのを思い出した。

「タイミング!」などと深夜に唸ってみるも仕方がないので、途中で読むのが止まっていた"ランウェイで笑って"の8巻を読み始めた。

アニメ化が決まったらしい。こちらも期待したい。


珍しく口内炎ができた。

人生で初めて口内炎ができたのは社会人になってから1ヶ月ほど経ったとき。

初めて感じる口内炎の痛みは痛烈ですぐさまGoogleで検索してみると「舌がん」の3文字が出てきて鬱になって布団にくるまった。

遡って、大学生のときに飲み会の席で口内炎になったことがないのが自分だけだったと判明した時があり、妙な優越感とともに疎外感を感じて酒が進まなかった。そしてきっと自分には縁のないものなんだろうなぁとそのときは思っていたが、てんで勘違いだった。

EZFGの「とても痛い痛がりたい」が口内炎の歌というのは有名な話。

僕はあの歌が好きだ。

なんの話だっけ。

今回の口内炎は舌の裏にできた。

こいつはだいぶタチが悪い。舌を動かすだけでもビリビリする。

生活リズムの乱れ、仕事のストレス、食事バランス。ため息が出るほど原因が思いつく。

とりあえずバッグに入っていたブラックのキシリトールガムを2錠口に入れてこのほとぼりが冷めるのを待つことにした。

そうだね アナタが耐えれば済むことだからね
そうやって 自分をごまかし続けて
フライアウェイ もう 
私の方からサインを送るよ
強がりばかりじゃ疲れるでしょ

とても痛い痛がりたい - EZFG

marshmallow-qa.com

0920 猫の地方性。

f:id:taiga006:20190920001240j:plain

猫の喧嘩で夜中に目が覚めた。

あなたにもそんな経験があるだろうか。

僕は今の横浜の家に引っ越してきてから季節に1度くらいの頻度でそれがある。

彼ら(彼女ら)はなんとも擬音化しづらい叫び声でお互いを威嚇し合う。

(ぴぎゃー!、んびゃ〜!あたりが近いかもしれない。)

不規則な周期で響く、その声で僕は目が覚める。 人間は狩猟民族なので大きな音より不規則な音に敏感だ、と昔誰かが言っていた。午前2時。

そうやって夜中に起こされるたびに僕は猫の地方性について少し考える。

僕が初めて一人暮らしをしたのは、仙台市に流れる広瀬川のほとりにある小さなアパートだった。

大学から徒歩10分で家賃3万4000円のロフト付き6畳のその部屋には大した思い出はないが、近所にとにかく野良猫が多かった。

観光地でもなんでもないが彼ら(そこの住む猫たちをあえて一括にする)はとにかく人懐っこかった。

合うたびに僕の足を外敵かなにかと勘違いして噛み付いてくる実家のネコとは大違いだった。(ナツ、君のことだよ。)

次に引っ越したのは寺と墓に囲まれた仙台駅徒歩3分のアパートだった。そこでも近所で野良猫を見かけることが多かった。

この頃から輪をかけて深夜に街を徘徊するのが趣味になった僕は、連れ立った体格差のある猫たちをよく見るようになった。家族ではないのだろう。野良猫の野良である部分を見てしまったような気がした。

「生まれ変わったら、ネコになりたい」とポエトリーな戯言(たわごと)をよく耳にするがラーメン屋の排気口の下で暖を取る猫たちに人間の言葉がわかったら容赦されないだろうな、きっと。

ちなみにこの文章では、"猫"と"ネコ"という表記にゆれがあるのだがあなたはその使い分けに気がついたであろうか。

僕はわからない。

marshmallow-qa.com

0919 防災マップ。

f:id:taiga006:20190918211105j:plain

横着な自分はポストの中のチラシをためがちだ。

毎日家を出るときにポストの中をチェックして、友人の結婚式の招待状やら水道代の請求書やら生活の上で必要なもの・避けられないものだけをピックアップして、隣町の不動産のチラシやらチェーンのピザ屋の割引券やらをつい放置してしまう。

塵も積もればなんとやら。そうこうして溜まった行き場のないチラシたちを月に一度くらいのペースでまとめて回収して家の中で取捨選択をする。(たまーに「え、これあったんじゃん!まず!」ってなる。ごくたまーに。)

この間もそんな感じで溜まりに溜まったチラシをぽいぽいとゴミ箱に捨てていた。そのとき、偶然地図を見つけた。 自分の住む横浜市の地区の防災マップだった。

「ほほーん。」

そのまま捨ててしまってもなんの問題もなかったのだが、妙に気になって広げてみると、それは自分が思っていたよりもだいぶ大きな代物だった。

「なるほどー。」

地図はエリアごとに色分けされていてその場所ごとの避難場所が目立つように書かれていた。

自分の住む場所は(大概の場所がそうであるように)このあたりの地域で一番大きな中学校だった。

台所の棚にしまってあった画鋲ケースを取り出して、玄関にその地図を貼ってみた。

僕は昔から地図が好きだった。

正確には地図を書くのが好きだった。

親の運転で一度通った場所は必ず覚えて、家に帰っては地図に書いて「おまえは記憶力がいいなー」と父に褒められた。

ノルウェイの森」に出てきた突撃隊という人物がいる。

彼は地図を愛し、国土地理院に入ることを目指す角刈りの学生だった。

本を読んだ多くの人にとって突撃隊は不思議なキャラで理解するのが難しい立ち位置のようだった。

物語の舞台からも途中で消えてしまう。

でも僕はこの青年がとても好きだった。

なんの、話だっけ。

そうだ、防災マップの話だ。

玄関に張った防災マップは僕の部屋の雰囲気からすると妙に浮いている。

そこだけ現実感が強いのだが、家の外に行く前、そして帰ってきたときに眺めるのにこれより良いものは今は思いつかない。

どうして早くポストからこいつを見つけ出さなかったのだろう。

そういうしょうもない、小さな後悔。

ちなみに村上春樹の作品は長編短編問わずほとんど読んできたが、「ノルウェイの森」が一番肌に合わなかった。

この話は長くなるし面白くならないことが見えているので割愛。

marshmallow-qa.com

0918 ヒグチアイ。

f:id:taiga006:20190918204012j:plain

最近は、ヒグチアイが好きだ。
きっかけはある土曜の夕方、消すのが面倒で流しっぱなしにしていたradikoから流れてきた彼女の歌声だった。
そのとき聴こえた曲名は忘れてしまったが、彼女の強い歌声とハーモニックな曲調に強く惹かれた。

便利な時代の便利なインターネットのおかげで僕はすぐに彼女の曲をYoutubeで聴くことができた。
それにしてもヒグチアイという名前がよい。本名なのかはたまた芸名というやつなのかそれはこの際どちらでもよい。
力強さと愛らしさを敷き詰めたような、収まりの良い5文字。
ところで僕の苗字はそれだけで5文字ある。メジャーな苗字でもないので自己紹介は苗字で済ませることが多い。
そのせいか特に名前を書くときは昔から名前のほうの数文字はどうも蛇足なような気がする。
決して嫌いな名前ではないのだけれど。
幕が閉じきる前の演者の小さなおふざけのような、お母さんにばれないように子供がかごに入れたスナック菓子のような、くすぐったい蛇足感。

でも、それが僕にとって多分ちょうどいいのだと思う。
僕がヒグチアイでないように、彼女も僕(の名前)ではないからあんな素敵な声で強いメッセージを歌えるのだと思う。

当たり前か。

一番の友だちは
裏側の自分だから

いつまでも勝てなくて
ときどきはつらくなる

迷った道で拾った何かを
ポケットにつめて

ぽたり - ヒグチアイ

marshmallow-qa.com

Golangで四則演算するだけのコンパイルができた。

🐬はじめに

speakerdeck.com

buiderscon2019でのDQNEOさんのライブコーディングの発表を見て「コンパイラ作るの夢ある〜面白そ〜」となったのでforkして0からやってみました。 といってGoで書いたのでほとんど写経。ちなみに更にその親玉のchibicc8ccなんかの実際のコードも見てみました。

github.com

📝メモ

...
        case '0', '1', '2', '3', '4', '5', '6', '7', '8', '9':
            intLiteral := readNumber(char)
            token := &Token{
                kind:  "intliteral",
                value: intLiteral,
            }
            tokens = append(tokens, token)
            fmt.Printf(" '%s'", token.value)
        case ';', '+', '-', '*', '/':
            token := &Token{
                kind:  "punct",
                value: string([]byte{char}),
            }
            tokens = append(tokens, token)
            fmt.Printf(" '%s'", token.value)
...

このあたりの部分はByteReaderさんが処理したものをTokenizerさんがTokenごとにうまく分割しているところ。
readNumberメソッドは数字がその後も続くようだったら最後まで見に行くやつ。

...
        switch token.value {
        case "+", "-", "*", "/":
            return &Expr{
                kind:     "binary",
                operator: token.value,
                left:     expr,
                right:    parseUnaryExpr(),
            }
...

このあたりはTokenの2つ目を見た後にそれが演算子Tokenだった場合はそれにさらに続くと期待される数値Tokenをパースさせようとするところ。
parseUnaryExprの中でparseUnaryExprを呼び出して再帰的になっている。

ちなみに余談なんですがアセンブリコードに出てくるmovq addqのqってなんなんだろう?と思って調べてみました。

検索して出てくるサンプルコードを見ていると、movq や addq ではなく mov, add と書かれているものもあります。q は quad word の略で、4 語長つまり 64bit データを扱うことを意味します。x86 では命令にビット長を明示指定することができ、b : byte (8bit)、w : word (16bit)、l : long word (32bit)、q : quad word (64bit) が指定できます。x86 はもともと 16bit CPU である 8086 から出発しているので、16bit を基準の語長(ワードサイズ)としています。

多くの場合、movq と書かず単に mov とだけ書けばアセンブラが自動的に適切な長さを判断してくれるのですが、この資料では長さを明示する方を選びました。

初学者向け x86/MacOSX 64bit アセンブリ

ということでqなくても問題なく動作しました。


root@e1219eb59aea:/mnt# echo -n '4*7' | go run main.go | ./asrun
------------ assembly(a.s) ------------
#Tokens: '4' '*' '7'

  .global main
main:
  mov $4, %rax
  mov $7, %rcx
  imul %rcx, %rax
  ret
------------    result     ------------
28
root@e1219eb59aea:/mnt# echo -n '12/3' | go run main.go | ./asrun
------------ assembly(a.s) ------------
#Tokens: '12' '/' '3'

  .global main
main:
  mov $12, %rax
  mov $3, %rcx
  mov $0, %rdx
  idiv %rcx
  ret
------------    result     ------------
4

てな具合で写経しながらではあるものの四則演算のできるアセンブリコードを吐かせることにも無事成功。

型があるとだいぶ楽ですね。
楽しかったのでまた続きをやる…かも?

参考

github.com

github.com

github.com

github.com

晩夏なのでGolangでAtCoder精選10問を解く。

f:id:taiga006:20190912171327j:plain


晩夏は特に関係ないです。 早速やっていき。

🐬 ABC 086 A - Product (100 点)

// ABC 086 A - Product
package main

import (
    "fmt"
)

func main() {
    var a, b int
    fmt.Scanf("%d %d", &a, &b)
    if (a*b)%2 == 0 {
        fmt.Println("Even")
    } else {
        fmt.Println("Odd")
    }
}

📝メモ

OddOddstypoしてWA出したけど内緒。 fmt.Scanは遅いらしいがとりあえずはまだ影響出るレベルではない。 そうなったとき考える。

↓そのあたりはこれが参考になりそう。 qiita.com

🐬 ABC 081 A - Placing Marbles (100 点)

// ABC 081 A - Placing Marbles
package main

import (
    "fmt"
)

func main() {
    var str string
    fmt.Scan(&str)
    cnt := 0
    for i := 0; i < len(str); i++ {
        if str[i] == '1' {
            cnt++
        }
    }
    fmt.Print(cnt)
}

📝メモ

与えられるのが数字列と決まっているでやりやすい。

🐬 ABC 081 B - Shift Only (200 点)

// ABC 081 B - Shift Only
package main

import "fmt"

func main() {
    var n, cnt int
    var a []int
    fmt.Scan(&n)
    a = make([]int, n)
    for i := 0; i < n; i++ {
        fmt.Scan(&a[i])
    }

    flag := true
    for flag {
        for i := 0; i < n; i++ {
            if a[i]%2 == 0 {
                a[i] /= 2
            } else {
                flag = false
            }
        }
        if flag {
            cnt++
        }
    }
    fmt.Print(cnt)
}

📝メモ

for flag で無限ループ。
すべてが偶数であれば一つでも偶数があればと読み間違えてWAを出した。

🐬 ABC 087 B - Coins (200 点)

// ABC 087 B - Coins
package main

import "fmt"

func main() {
    var A, B, C, X, cnt int
    fmt.Scan(&A, &B, &C, &X)

    for a := 0; a <= A; a++ {
        for b := 0; b <= B; b++ {
            for c := 0; c <= C; c++ {
                if a*500+b*100+c*50 == X {
                    cnt++
                }
            }
        }
    }
    fmt.Println(cnt)
}

📝メモ

全探索。三重ループは見るだけで心的負荷が高い。

🐬 ABC 083 B - Some Sums (200 点)

// ABC 083 B - Some Sums 
package main

import (
    "fmt"
    "log"
)

func main() {
    var n, a, b, total int
    fmt.Scan(&n, &a, &b)

    for i := 1; i < (n + 1); i++ {
        var x [3]int
        var y int
        if i >= 1000 {
            x[0] = i / 1000
        }
        if i >= 100 {
            x[1] = i / 100
        }
        if i >= 10 {
            x[2] = i / 10
        }

        y = i - x[0]*1000 - x[1]*100 - x[2]*10
        res := x[0] + x[1] + x[2] + y

        if res >= a && res <= b {
            total += i
            log.Printf("n = %d -> res:%d", i, res)

        }
    }
    fmt.Print(total)
}

📝メモ

これもA以上B以下の条件をAorBに等しくなると取り間違えて最初にWAを出してしまった。途中のデバッグログは反省として消さずに残しておく。

🐬 ABC 088 B - Card Game for Two (200 点)

// ABC 088 B - Card Game for Two
package main

import (
    "fmt"
    "sort"
)

func main() {
    var n, a int
    fmt.Scan(&n)
    arr := make([]int, n)
    for i := range arr {
        fmt.Scan(&a)
        arr[i] = a
    }
    sort.Sort(sort.Reverse(sort.IntSlice(arr)))

    var alice, bob int
    for i := range arr {
        if i%2 == 0 {
            alice += arr[i]
        } else {
            bob += arr[i]
        }
    }
    fmt.Println(alice-bob)
}

📝メモ

sort packageを使って解決。(降順にする方法がわからずに調べた。)
golangのsortに関してはいろいろ気になるところがあったので後日また記事にする。

🐬 ABC 085 B - Kagami Mochi (200 点)

// ABC 085 B - Kagami Mochi
package main

import "fmt"

func main() {
    var n int
    fmt.Scan(&n)
    d := make([]int, n)
    for i := 0; i < n; i++ {
        fmt.Scan(&d[i])
    }
    p := make(map[int]int)
    for v := range d {
        p[d[v]]++
    }
    fmt.Println(len(p))
}

📝メモ

mapを使ってカウント。問題の意図を間違えなければ非常に単純。

🐬 ABC 085 C - Otoshidama (300 点)

// ABC 085 C - Otoshidama
package main

import "fmt"

func main() {
    var n, y int
    fmt.Scan(&n, &y)

    for i := 0; i <= n; i++ {
        for j := 0; j <= (n - i); j++ {
            k := n - (i + j)
            total := 10000*i + 5000*j + 1000*k
            if total == y {
                fmt.Println(i, j, k)
                return
            }
        }
    }
    fmt.Println(-1, -1, -1)
}

📝メモ

素直にやったらTLEになりそうだったのでちょっと工夫した。

🐬 ABC 049 C - Daydream (300 点)

// ABC 049 C - Daydream
package main

import (
    "fmt"
    "strings"
)

func main() {

    var s string
    fmt.Scan(&s)

    s = reverse(s)
    s = strings.Replace(s, "resare", "", -1)
    s = strings.Replace(s, "esare", "", -1)
    s = strings.Replace(s, "remaerd", "", -1)
    s = strings.Replace(s, "maerd", "", -1)

    var res string
    if len(s) == 0 {
        res = "YES"
    } else {
        res = "NO"
    }
    fmt.Println(res)
}

func reverse(s string) string {
    rs := []rune(s)
    for i, j := 0, len(s)-1; i < j; i, j = i+1, j-1 {
        rs[i], rs[j] = rs[j], rs[i]
    }
    return string(rs)
}

📝メモ

文字列の反転。自前で実装する必要があった。ただindexを見て反転させていくとバイト列なのでぐちゃぐちゃになってしまう。runeを使う。

y0m0r.hateblo.jp

🐬 ABC 086 C - Traveling (300 点)

// ABC 086 C - Traveling
package main

import (
    "fmt"
    "math"
)

func main086C() {
    var n int
    fmt.Scan(&n)

    var t int
    var x, y float64
    t, x, y = 0, 0.0, 0.0 // initialized

    var tNext int
    var xNext, yNext float64

    flag := "Yes"
    for i := 0; i < n; i++ {
        fmt.Scan(&tNext, &xNext, &yNext)

        // 残り時間
        T := tNext - t
        // 目的地までの距離(マンハッタン距離)
        dist := math.Abs(xNext-x) + math.Abs(yNext-y)

        // 残り時間より必要な移動距離のほうが長い
        if T < int(dist) {
            flag = "No"
        }
        // 着いてからのあまり時間が偶数であれば行き帰りできる
        if (T-int(dist))%2 == 1 {
            flag = "No"
        }
        // updated
        t, x, y = tNext, xNext, yNext
    }
    fmt.Println(flag)
}

📝メモ

自分で解けなかったので、答えを調べる。この人の説明がわかりやすかった。

scrapbox.io


Gistにも同じコードを載せてあります。 AtCoder過去問精選10問 Golangで解いてみた · GitHub

自分のcommit logだけを見たい!author,committerの違いとは。

チームで開発しているレポジトリの場合、自分もしくは他の誰かがコミットした情報のみをまとめて確認したいというケースが稀にある。

$ git log --author=[user_name]

もしくは

$ git log --committer=[user_name]

で検索ができる。
と、ここまでは検索すればすぐに出てくるが、このauthor or committer の違いをわかっていない分にはこれだとなんとももどかしい。
ということで調べた。


git はすべてのcommitにAuthorとCommitterの情報を記録している。

- Authorはコードを書いた人
- Committerはリポジトリにコミットした人

この違いは過去のコミットを操作した際などに重宝される。

つまり、ある人がコードを書いてそれをコミットしたあとにgit commit --amend などで他の誰かが改変した場合にもAuthorは変更されず、あくまでCommitterのみが変更される。

ちなみにAuthorごと過去を改変することも可能なようだが、あまり利用ケースが思いつかない。その人がいた事自体を消したい場合、あるいは見せたくない本名やアドレスが含まれていた場合などだろうか…?

通常の git log コマンドではAuthorしか表示されない。

Committerも一緒に表示させるにはoptionをつけて git log --pretty=full などとするとよい。

参考)

git-scm.com

stackoverflow.com

DUO-CAPTURE EXが電池駆動で動かない!

本体背面の[COMPUTER / TAB]スイッチをTABのほうにスイッチさせないと電池で駆動しない。

なお接続する機器すべての電源を切っている状態でないとここをスイッチするのは危ない。

サンプリング周波数が[COMPUTER / TAB]で異なる。(後者の方が44.1kHz固定で低い。)

それからこのAIFは電池で駆動している場合は本体表面の電源ランプが赤になる(ふだんは緑)。


普段、ACアダプタからの給電で駆動させていたので気がつかなかった。

立ち会った友人がネットで取扱説明書を読んで気が付いた。ちゃんと読みましょう...。

(ところで、もうこいつを買ってから6年経っていることをAmazonの購入履歴を見て知った。)

www.roland.com

Roland ローランド オーディオインターフェイス DUO-CAPTURE EX UA-22

Roland ローランド オーディオインターフェイス DUO-CAPTURE EX UA-22

Golangのフォーマット指定子についてカンペを作っておいた。package fmt

たびたびGolangのフォーマット指定子まわりについて困惑してfmtのdocを見たり検索したりしているので、知識を整理する目的でGistにまとめておきます。(+vとか#vとか。)

参考

godoc.org

blog.y-yuki.net

qiita.com

oohira.github.io