型なき言語に付ける型

公開日:

Clusterバーチャル空間で開催された『バーチャル空間勉強会#0』でライトニングトーク(5分)として発表しました。

Download PDF

スライドテキスト

Page 1

型なき言語に付ける型

Type in untyped languages

#virtual_study_group バーチャル空間勉強会#0

Page 2

お前誰よ
うさみけんた (@tadsan)

/ Zonu.EXE

  • GitHub/Packagistでは id: zonuexe
    • ピクシブ株式会社 pixiv運営本部
  • Emacs Lisper, PHPer, Rubyist
  • Emacs PHP Modeのメンテナ引き継ぎました
    • 好きなリスプはEmacs Lispです
    • Qiitaに記事を書いたり変なコメントしてるよ

Page 3

Page 4

Page 5

近況

Page 6

Page 7

Page 8

話しました

Page 9

Page 10

Page 11

Page 12

仕方がないので全 然違う話をします

Page 13

本日のお題

Page 14

型、ついて ますか?

Page 15

型については結構 雑な印象で見解を
語るひとが多い

Page 16

俺も俺も

Page 17

型があるから変更に強い
というひとも居れば、
型がないから変更に強い
というひとも居る

Page 18

???

Page 19


よくわからん

Page 20

私もだ

Page 21

intとboolとか
でしょ

Page 22

Page 23

読むがよい

Page 24

‒Benjamin C. Pierce 著/住井英二郎 監訳/遠藤侑介・酒井政裕・今井敬吾・黒木裕介・
今井宜洋・才川隆文・今井健男 訳 『型システム入門 プログラミング言語と型の理論』
(オーム社、978-4-274-06911-6、2013年)サンプル

Page 25

‒Benjamin C. Pierce 著/住井英二郎 監訳/遠藤侑介・酒井政裕・今井敬吾・黒木裕介・
今井宜洋・才川隆文・今井健男 訳 『型システム入門 プログラミング言語と型の理論』
(オーム社、978-4-274-06911-6、2013年)サンプル

Page 26

(一章はサンプルとし てPDFが無料でダウ
ンロードできます)

Page 27

正しい、完璧に 正しいのだが

Page 28

最初から
用語多すぎ

Page 29

説明の抽象度が
高すぎて現実との ギャップ大きすぎ

Page 30

この1章の内容を解き ほぐして説明するだけ
で何時間も話せそう

Page 31

そのほかの型とかプロ グラミング言語論の本 を読むと数式みたいな
のが出てきてワケワカラン

Page 32

型について
ちょっと知りたい
だけなのに

Page 33

世の中の
人と型

Page 34

型を使っているが 思索の対象として
向き合ってないひと

Page 35

特定の言語の型とだ
け向き合ってる人

Page 36

抽象概念の型と
向き合ってるひと

Page 37

いろんな
背景の人が居る

Page 38

動的言語を使っていると 静的型付き言語利用者か ら冷ややかに見られがち

Page 39

やーい
型なし型なし

Page 40

型はあるんだ!
実行時にあるんだ!

Page 41

そういうことをまじめに 主張すると憐れみを湛え
た目で見られはじめる

Page 42

真の型なし言語も 複数あるが今回は
割愛しました

Page 43


わかりたく ないですか

Page 44

このトークに
結論はない

Page 45

実際の言語の型から
いきましょう

Page 46

C言語

Page 47

よくわからんけど型がだるい

#include <stdio.h>

long add(long a, long b) {
return a + b;
}

int main(void) {
unsigned int x = 1, y = 2;

printf("%d + %d = %d\n", x, y, add(x, y));
}

Page 48

私たちFラン情報科学生は 情弱なのでまともな説明 もないカビの生えた教科
書でC言語を叩き込まれる

Page 49

私の入門者時代のC
言語理解は曖昧
なので曖昧なままで
次の話に進めます

Page 50

さておき

Page 51

短くなってべんり

// JavaScript

function add(a, b) {
return a + b;
}

const x = 1, y = 2;

console.log(`${x} + ${y} + ${add(x, y)}`);

Page 52

もっと短くなってべんり

# Ruby

def add(a, b)
a + b
end

x = 1; y = 2

puts "#{x} + #{y} + #{add x, y}"

Page 53

そういう俺たちが
動的言語に触れると
こうなる

Page 54

型とか
要らんやろw

Page 55

そうだな

Page 56

見ればわかるだろ

# Ruby

オブジェクトが生えてたら何でもいい

# to_s
def show(obj)
puts obj.to_s
end

Page 57

常識的に考えて

# Ruby

足し算できるものならなんでもいいし

# 

ジェネリクスとかなくてもいいw

#
def add(a, b)
a + b
end


def show(obj)
puts obj.to_s
end

Page 58

引数が少ないうちはな…

# Ruby

user = User.findBy(id: params[:user_id])

Page 59

引数が増えてくると

# Ruby

obj = palpunte(
user_id,
????, ????, ????,
)

p obj

Page 60

実装を直接見に
行く機会が増える

Page 61

引数が増えてくると

# Ruby

実装を見ないと期待するオプションに何を渡せばいいのか

#
def palpunte (id, foo, bar, buz)
p [id, foo, bar, buz]
end
というか見てもよくわからない

#

Page 62

素朴に書くと引数がわからん

# Ruby

実際にはキーワード引数だけで表現できる

#
def palpunte (id: nil, **options)
raise TypeError if id.nil?

foo ||= "default foo" bar ||= "default bar" buz ||= "default buz"

p [id, foo, bar, bar]]
end

Page 63

だんだん型チェックが増えてく

# Ruby

raise TypeError unless foo.instance_of?(String) raise TypeError unless bar.instance_of?(String) raise TypeError unless buz.instance_of?(String)

Page 64

いわゆる動的言語 にも型が付く流れ

Page 65

Flowtype TypeScript

Page 66

PEP484
mypy

Page 67

Ruby3 rbi
Sorbet Steep

Page 68

PHP型宣言

PHPDoc
PhpStorm,Phan

Page 69

身体は型を
求める

Page 70

型が付いていない
ということは
どういうことか

Page 71

可能性は無限大

<?php

/**

可能性は無限大

* @param mixed $a * @param mixed $b
* @return mixed
*/
function add($a, $b)
{
return $a + $b;
}

Page 72

仮引数宣言がない言語

<?php

function add()
{
$args = func_get_args();

return array_pop($args) + array_pop($args);
}

Page 73

無限大じゃ 困るんだよ

Page 74

とはいえ+できる
値という前提がある
ので案外困らない

Page 75

ほんとに?

Page 76

PHPの演算子の暗黙的型変換

<?php

error_reporting(0);

想定通り

var_dump(add(1, 2)); // => int(3)

許容範囲

var_dump(add(1.0, 2.0)); // => float(3.0)

許容範囲

var_dump(add('1', '2')); // => int(3)
var_dump(add('', '')); // => int(0) ????? var_dump(add(1, 2, 3)); // => int(3) ?????

えっ

var_dump(add([], [])); // => [] ?????
var_dump(add(PHP_INT_MAX, 1)); 
 // => float(9.2233720368548E+18)

Page 77

実行時に
型を調べよう

Page 78

いわゆる動的言語は 実行時に型があるの でそれを検査できる

Page 79

JavaScriptでは typeof 演算子で
型名文字列がとれる

Page 80

Python type()
Ruby Object#class

Page 81

PHPではis_int(),
is_string()などの関数
(gettypeは使いにくい)

Page 82

可能性を絞り込もう

<?php

/**

可能性は無限大

* @param mixed $a

可能性は無限大

* @param mixed $b
* @return mixed
*/
function add($a, $b)
{
if (!is_int($a)) {
throw new TypeError('Error');
}
if (!is_int($b)) {
throw new TypeError('Error');
}

実装するときに 以外の値が渡ってくる可能性を考えなくて良い

// int
return $a + $b;
}

Page 83

実行時に変な値に対 して処理が続行する 可能性は避けられる

Page 84

例外で処理が 停止するので

Page 85

PHPとかいう
静的型付き
プログラミング言語

Page 86

静的型付きPHP

<?php declare(strict_types=1);

このメソッドを実装するときに 以外の値が

// int
渡ってくる可能性は考えなくてよい

//
function add(int $a, int $b): int
{
return $a + $b;
}

Page 87

静的 =
実行しなくても
型が決まってる状態

Page 88

静的型付き

Statically typed
既に型が決定してる

Page 89

動的型付け

Dynamic typing
実行時に型を付ける

Page 90

よくある誤解
静的型=コンパイラ
動的型=インタプリタ

Page 91

ただしプログラム実行時
のデータの表現方法が
そういう関係になりがち

Page 92

C言語は
静的型付き

Page 93

多くの動的言語 はC言語で実装

Page 94

必ずしも排他の
関係ではない

Page 95

お使いの言語ランタイム(ruby, python, phpなど)のC言語実装 がどうなっているか、変数がC言 語の型でどう表現されてるか読ん
でみるとおもしろいと思います

Page 96

PHPは実行時に 型をチェックする

Page 97

ただし関数と
プロパティに静的に
型を付けられる

Page 98

ただし静的に型を付けて も実行時にクラッシュす
る可能性があります

Page 99

型で守られてると はどういう状態か

Page 100

‒Akinori Abe 『型安全性入門』(Apr 6, 2017)

Page 101

‒Akinori Abe 『型安全性入門』(Apr 6, 2017)

Page 102

関数を呼び出す側が間 違って呼び出すことを PHPだけでは防げない

Page 103

動的言語で完全かつ
健全にするのは
不可能

Page 104

偽陽性(動かないのに動き そうなフリをしている)こ とを最小にしていくこと
を目指す

Page 105

コンパイラの代りに
静的型チェッカーを使 おうということになる

Page 106

PHPでも複数の 型チェッカーが
揃っている

Page 107

PhpStorm
Phan, Psalm
PHPStan

Page 108

PHPのソースコードを 解析しても判別できな い型は注釈(annotate) してあげる必要がある

Page 109

人間が
コメントで
型を書く

Page 110

人間が型を間違って つけると破綻するの で実際簡単ではない

Page 111

連想配列(Hash, dict)
を構造体のつもりで
多用されると静的解析
を簡単に破滅できる

Page 112

と思うでしょ? PHPDocでなら 型をつけられます

Page 113

PHPに型を付けたり
CIに載せる話は
FANBOXに記事やス ライドを掲載してます

Page 114

Page 115

型について学ぶに はどうすればいい

Page 116

Page 117

ハードルが高い
(そもそも値段が…)

Page 118

一章のPDFは無料なので 読んでほしいが難しいの で理解できなくてもいい

Page 119

Page 120

型のみならずプログラミ ング言語についてのさま
ざまな概念を学べる

Page 121

まとめ

Page 122

仕事で使ってる言語を好 きになるために目を逸ら
さず向き合っていこう