SlideShare ist ein Scribd-Unternehmen logo
1 von 95
Downloaden Sie, um offline zu lesen
#kbkz_tech




class HogeOperation {
private(set) var isPrepared = false
func prepare() {
guard !isPrepared else {
fatalError("prepare を複数回呼ばないこと")
}
isPrepared = true
}
}
// Init 状態の HogeOperation を生成
let operation = HogeOperation<Init>()
// 最初は prepared を呼べて準備完了したものを取得可能
let preparedOp = operation.prepared()
// 準備が終われば prepared はビルドエラーで実行不可
preparedOp.prepared()
// これで "操作状態を表現する型" を表現
protocol OperationState {}
// 操作状態ごとにクラスを定義
class Init: OperationState {}
class Prepared: OperationState {}
// 型パラメーターで型に状態を付与
class HogeOperation<State: OperationState> {
/*
今回は内部で、
型パラメーターを使わないのがポイント
*/
}
extension HogeOperation where State: Init {
// 準備を実行し、準備完了状態のインスタンスを返す
func prepared() -> HogeOperation<Prepared> {…}
}
extension HogeOperation where State: Prepared {
// 目的の操作を実行する
func execute() {…}
}
let operation = HogeOperation<Init>()
// Init 状態では、まだ execute は存在しない
operation.execute()
// prepared を呼ぶことで Prepared 状態のものを取得
let preparedOp = operation.prepared()
// Prepared 状態には、もう prepared は存在しない
preparedOp.prepared()
let operation = HogeOperation<Init>()
// HogeOperation<Init> 型だから prepared が呼べる
let preparedOp: HogeOperation<Prepared>()
= operation.prepared()
// HogeOperation<Prepared> 型だから execute が呼べる
preparedOp.execute()
// Init クラスや Prepared クラスを、実行時には使わない
// ビルドの段階で、もう役目が済んでいる
let operation = HogeOperation<Init>()
let preparedOp = operation.prepared()
let type1 = type(of: operation)
let type2 = type(of: preparedOp)
type1 == type2 // false
// 型パラメーターで型に状態を付与
class HogeOperation<State: OperationState> {
/*
内部では、型パラメーターを使っていない
型の在り方を説明するためだけに使っている
*/
/// Phantom Type に出逢う前の認識
// Array はテンプレート的なもので…
struct Array<Element> {
}
// 型パラメーターによって、異なる型になる
let values: Array<Int> = Array<String>()
// protocol OperationState {}
// class Init: OperationState {}
// class Prepared: OperationState {}
class Operation {
fileprivate var data: OperationData
fileprivate init(data: OperationData) {
self.data = data
}
func mob() {}
}
class OperationInit: Operation {
convenience init() {…}
func prepared() -> OperationPrepared {…}
}
class OperationPrepared: Operation {
func execute() {…}
}
let operation = OperationInit()
let preparedOp = operation.prepared()
preparedOp.execute()
struct OperationInit {
fileprivate var data: OperationData
fileprivate init(data: OperationData) {…}
// 共通機能
func mob() {}
// 固有の機能
init() {…}
func prepared() -> OperationPrepared {…}
}
struct OperationPrepared {
fileprivate var data: OperationData
fileprivate init(data: OperationData) {…}
// 共通機能
func mob() {}
// 固有の機能
func execute() {…}
}
let operation = OperationInit()
let preparedOp = operation.prepared()
preparedOp.execute()
protocol Operation {}
struct OperationInit: Operation {
…
}
struct OperationPrepared: Operation {
…
}
struct Operation {
struct Init {
…
}
struct Prepared {
…
}
}
let operation = Operation.Init()
let preparedOp = operation.prepared()
preparedOp.execute()
class Operation {
fileprivate var data: OperationData
fileprivate init(data: OperationData) {
self.data = data
}
func mob() {}
}
extension Operation {
class Init: Operation {
…
}
class Prepared: Operation {
…
}
}
let operation = Operation.Init()
let preparedOp = operation.prepared()
preparedOp.execute()
class HogeOperation<State: OperationState> {
func mob() {…}
}
extension HogeOperation where State: Init {
func prepared() -> HogeOperation<Prepared> {…}
}
extension HogeOperation where State: Prepared {
func execute() {…}
}
let operation = HogeOperation<Init>()
operation.execute()
let operation = OperationInit()
operation.execute()
// 準備前と準備後を、自分自身や同じ変数に書き戻せない
var operation = HogeOperation<Init>()
operation = operation.prepared()
protocol Operation {}
class HogeOperation<State: OperationState>: Operation {
}
var op: Operation
op = HogeOperation<Init>()
op = (op as! HogeOperation<Init>).prepared()
op = (op as! HogeOperation<Prepared>).execute()
class Driver {
init(channel: Int? = nil, volume: Int? = nil,
pan: Int? = nil, format: Format? = nil,
route: Route? = nil) {
}
}
// 設定項目に何があるかや、設定順番に気を使う
let driver = Driver(volume: 10,
format: ulaw, route: .speaker)
// 本体のクラスを Phantom Type で定義して…
class Driver<State> where State: AudioState {
}
// 準備が整ったときの機能を実装し…
extension Driver where State: Ready {
func start() { … }
}
// 初期化中にできることを規定すると…
extension Driver where State: Setup {
func prepared() -> Driver<Ready> { … }
func set(channel: Int) -> Driver { return self }
func set(volume: Int) -> Driver { return self }
func set(pan: Int) -> Driver { return self }
func set(format: Format) -> Driver { return self }
func set(route: Route) -> Driver { return self }
}
// 初期設定では、順番を気にせず設定できる・補完が効く
let driver = Driver<Setup>()
.set(format: ulaw)
.set(volume: 10)
.set(route: .speaker)
.prepared() // ここで Driver<Ready>() を返す
// 設定完了を宣言 (prepared) して、使い始める
driver.start()
let driver = Driver<Setup>()
.format // → Driver<FormatSetup>
.set(sampleRate: 44100)
.set(channelsPerFrame: 2)
.general // → Driver<GeneralSetup>
.set(volume: 10)
.set(route: .speaker)
.prepared() // → Driver<Ready>
let driver = Driver.setup() // → DriverSetup
.format // → FormatSetup
.set(sampleRate: 44100)
.set(channelsPerFrame: 2)
.general // → AudioSetup
.set(volume: 10)
.set(route: .speaker)
.prepared() // → Driver
// 設定項目を、初期値を持った構造体で用意して…
struct Description {
var channel: Int = default
var volume: Int = default
var pan: Int = default
var format: Format = default
var route: Route = default
}
let description = Description()
description.format.sampleRate = 44100
description.format.channelsPerFrame = 2
description.volume = 10
description.route = .speaker
// Driver は Description で初期化するようにして…
class Driver {
init(description: Description) { … }
}
// 設定項目を渡して、初期化を完成する
let driver = Driver(description: description)
class Controller {
var environment: Environment<Neutral>
}
struct Environment<State> {
fileprivate(set) var platform: Platform
fileprivate(set) var version: Double
func startEditing() -> Environment<Editing> {
return Environment<Editing>(
platform: platform, version: version)
}
}
extension Environment where State: Editing {
mutating func set(platform: Platform) { … }
mutating func set(version: Double) { … }
func endEditing() -> Environment<Neutral> {
return Environment<Neutral>(
platform: platform, version: version)
}
}
func update() {
// 編集状態で取り出さないと、書き込めない
var environment = self.environment.startEditing()
environment.set(platform: .macOS)
environment.set(version: Platform.macOS.latest)
// ローカルで編集を終了したら、書き戻す
self.environment = environment.endEditing()
}
extension Environment where State: Editing {
var platform: Platform
var version: Double
// 同じ内容の、別インスタンスを作り直している
func endEditing() -> Environment<Neutral> {
return Environment<Neutral>(
platform: platform, version: version)
}
extension Environment where State: Editing {
// 内容を原始的にコピーしないといけないとき
func endEditing() -> Environment<Neutral> {
var result = Environment<Neutral>()
result.platform = platform
result.version = version
return result
}
struct Environment<State> {
fileprivate(set) var platform: Platform
fileprivate(set) var version: Double
}
extension Environment {
fileprivate init<S>(takeover: Environment<S>) {
platform = takeover.platform
version = takeover.version
}
}
extension Environment where State: Editing {
func endEditing() -> Environment<Neutral> {
return Environment<Neutral>(takeover: self)
}
}
struct Environment<State> {
// データをここで集中管理する
fileprivate struct Context {
var platform: Platform
var version: Double
}
// これだけを引き継げば済む状況を作る
fileprivate var _context: Context
}
extension Environment {
fileprivate init(context: Context) {
_context = context
}
}
extension Environment where State: Editing {
func endEditing() -> Environment<Neutral> {
return Environment<Neutral>(context: _context)
}
}
extension Environment {
var platform: Platform {
get { _context.platform }
set { _context.platform = newValue }
}
var version: Double {
get { _context.version }
set { _context.version = newValue }
}
extension Environment where State: Editing {
func endEditing() -> Environment<Neutral> {
// 準備不要で、いきなりビットキャスト可能
return unsafeBitCast(self,
to: Environment<Neutral>.self)
}
}
extension Environment {
fileprivate init<S>(takeover: Environment<S>) {
self = unsafeBitCast(takeover,
to: Environment.self)
}
}
let sub: Base = Sub()
let base: Base = Base()
// 実体が Sub なので、全ての機能が使える
let obj: Sub = unsafeBitCast(sub, to: Sub.self)
// 実体が Base なので、Sub の機能を使うとクラッシュする
let obj: Sub = unsafeBitCast(base, to: Sub.self)
class Test: OperationState {}
extension HogeOperation where State: Test {
func testSomething() {…}
}
extension HogeOperation where State: Init {
func testing() -> HogeOperation<Test> {…}
}
// Test 状態を Prepared から継承させれば…
class Test: Prepared {}
// Test には Prepared の機能も備わる
extension HogeOperation where State: Prepared {
func execute() {…}
}
extension HogeOperation where State: Test {
func testSomething() {…}
}
Understanding Phantom Types in Swift
Understanding Phantom Types in Swift
Understanding Phantom Types in Swift
Understanding Phantom Types in Swift

Weitere ähnliche Inhalte

Was ist angesagt?

Debugging: Rules & Tools
Debugging: Rules & ToolsDebugging: Rules & Tools
Debugging: Rules & ToolsIan Barber
 
関西PHP勉強会 php5.4つまみぐい
関西PHP勉強会 php5.4つまみぐい関西PHP勉強会 php5.4つまみぐい
関西PHP勉強会 php5.4つまみぐいHisateru Tanaka
 
Building apache modules
Building apache modulesBuilding apache modules
Building apache modulesMarian Marinov
 
Php unit the-mostunknownparts
Php unit the-mostunknownpartsPhp unit the-mostunknownparts
Php unit the-mostunknownpartsBastian Feder
 
Utility Modules That You Should Know About
Utility Modules That You Should Know AboutUtility Modules That You Should Know About
Utility Modules That You Should Know Aboutjoshua.mcadams
 
Function Call Optimization
Function Call OptimizationFunction Call Optimization
Function Call Optimizationppd1961
 
Code Generation in PHP - PHPConf 2015
Code Generation in PHP - PHPConf 2015Code Generation in PHP - PHPConf 2015
Code Generation in PHP - PHPConf 2015Lin Yo-An
 
Optimizing mysql stored routines uc2010
Optimizing mysql stored routines uc2010Optimizing mysql stored routines uc2010
Optimizing mysql stored routines uc2010Roland Bouman
 
Mocking Dependencies in PHPUnit
Mocking Dependencies in PHPUnitMocking Dependencies in PHPUnit
Mocking Dependencies in PHPUnitmfrost503
 
Writing MySQL User-defined Functions in JavaScript
Writing MySQL User-defined Functions in JavaScriptWriting MySQL User-defined Functions in JavaScript
Writing MySQL User-defined Functions in JavaScriptRoland Bouman
 
Advanced php testing in action
Advanced php testing in actionAdvanced php testing in action
Advanced php testing in actionJace Ju
 
3. writing MySql plugins for the information schema
3. writing MySql plugins for the information schema3. writing MySql plugins for the information schema
3. writing MySql plugins for the information schemaRoland Bouman
 
Devinsampa nginx-scripting
Devinsampa nginx-scriptingDevinsampa nginx-scripting
Devinsampa nginx-scriptingTony Fabeen
 
Perl Sucks - and what to do about it
Perl Sucks - and what to do about itPerl Sucks - and what to do about it
Perl Sucks - and what to do about it2shortplanks
 
Using ngx_lua in UPYUN 2
Using ngx_lua in UPYUN 2Using ngx_lua in UPYUN 2
Using ngx_lua in UPYUN 2Cong Zhang
 

Was ist angesagt? (20)

Debugging: Rules & Tools
Debugging: Rules & ToolsDebugging: Rules & Tools
Debugging: Rules & Tools
 
関西PHP勉強会 php5.4つまみぐい
関西PHP勉強会 php5.4つまみぐい関西PHP勉強会 php5.4つまみぐい
関西PHP勉強会 php5.4つまみぐい
 
Django
Django Django
Django
 
Building apache modules
Building apache modulesBuilding apache modules
Building apache modules
 
Php unit the-mostunknownparts
Php unit the-mostunknownpartsPhp unit the-mostunknownparts
Php unit the-mostunknownparts
 
Utility Modules That You Should Know About
Utility Modules That You Should Know AboutUtility Modules That You Should Know About
Utility Modules That You Should Know About
 
Function Call Optimization
Function Call OptimizationFunction Call Optimization
Function Call Optimization
 
How to ride a whale
How to ride a whaleHow to ride a whale
How to ride a whale
 
Workshop unittesting
Workshop unittestingWorkshop unittesting
Workshop unittesting
 
Code Generation in PHP - PHPConf 2015
Code Generation in PHP - PHPConf 2015Code Generation in PHP - PHPConf 2015
Code Generation in PHP - PHPConf 2015
 
Gun make
Gun makeGun make
Gun make
 
Optimizing mysql stored routines uc2010
Optimizing mysql stored routines uc2010Optimizing mysql stored routines uc2010
Optimizing mysql stored routines uc2010
 
Mocking Dependencies in PHPUnit
Mocking Dependencies in PHPUnitMocking Dependencies in PHPUnit
Mocking Dependencies in PHPUnit
 
Writing MySQL User-defined Functions in JavaScript
Writing MySQL User-defined Functions in JavaScriptWriting MySQL User-defined Functions in JavaScript
Writing MySQL User-defined Functions in JavaScript
 
Advanced php testing in action
Advanced php testing in actionAdvanced php testing in action
Advanced php testing in action
 
3. writing MySql plugins for the information schema
3. writing MySql plugins for the information schema3. writing MySql plugins for the information schema
3. writing MySql plugins for the information schema
 
High Performance tDiary
High Performance tDiaryHigh Performance tDiary
High Performance tDiary
 
Devinsampa nginx-scripting
Devinsampa nginx-scriptingDevinsampa nginx-scripting
Devinsampa nginx-scripting
 
Perl Sucks - and what to do about it
Perl Sucks - and what to do about itPerl Sucks - and what to do about it
Perl Sucks - and what to do about it
 
Using ngx_lua in UPYUN 2
Using ngx_lua in UPYUN 2Using ngx_lua in UPYUN 2
Using ngx_lua in UPYUN 2
 

Andere mochten auch

Minimal Cake Pattern in Swift
Minimal Cake Pattern in SwiftMinimal Cake Pattern in Swift
Minimal Cake Pattern in SwiftHikaru Yoshimura
 
Androidオールスターズ2016 yanzm
Androidオールスターズ2016 yanzmAndroidオールスターズ2016 yanzm
Androidオールスターズ2016 yanzmYuki Anzai
 
なるべくコードを書かないAndroid開発
なるべくコードを書かないAndroid開発なるべくコードを書かないAndroid開発
なるべくコードを書かないAndroid開発Hiroshi Kikuchi
 
はじめようlocalization
はじめようlocalizationはじめようlocalization
はじめようlocalizationJoão Orui
 
Advance text rendering in i os
Advance text rendering in i osAdvance text rendering in i os
Advance text rendering in i osConfiz
 
Hi performance table views with QuartzCore and CoreText
Hi performance table views with QuartzCore and CoreTextHi performance table views with QuartzCore and CoreText
Hi performance table views with QuartzCore and CoreTextMugunth Kumar
 
日本の祝祭日を計算してカレンダ-に表示するアプリサンプル
日本の祝祭日を計算してカレンダ-に表示するアプリサンプル日本の祝祭日を計算してカレンダ-に表示するアプリサンプル
日本の祝祭日を計算してカレンダ-に表示するアプリサンプルFumiya Sakai
 
What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...
What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...
What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...将之 小野
 
リテラルと型の続きの話 #__swift__
リテラルと型の続きの話 #__swift__リテラルと型の続きの話 #__swift__
リテラルと型の続きの話 #__swift__Tomohiro Kumagai
 
バ、バカな...!ハッカソンの中で成長しているだと...!?
バ、バカな...!ハッカソンの中で成長しているだと...!?バ、バカな...!ハッカソンの中で成長しているだと...!?
バ、バカな...!ハッカソンの中で成長しているだと...!?Kenji Tanaka
 
多人数iOSアプリ開発を考える
多人数iOSアプリ開発を考える多人数iOSアプリ開発を考える
多人数iOSアプリ開発を考えるsasaron 397
 
Web エンジニアが postgre sql を選ぶ 3 つの理由
Web エンジニアが postgre sql を選ぶ 3 つの理由Web エンジニアが postgre sql を選ぶ 3 つの理由
Web エンジニアが postgre sql を選ぶ 3 つの理由Soudai Sone
 
Swift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorp
Swift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorpSwift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorp
Swift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorpTomohiro Kumagai
 
アメブロの大規模システム刷新と それを支えるSpring
アメブロの大規模システム刷新と それを支えるSpringアメブロの大規模システム刷新と それを支えるSpring
アメブロの大規模システム刷新と それを支えるSpringTakuya Hattori
 
20170302 tryswift tasting_tests
20170302 tryswift tasting_tests20170302 tryswift tasting_tests
20170302 tryswift tasting_testsKazuaki Matsuo
 
Type-safe Web APIs with Protocol Buffers in Swift at iOSCon
Type-safe Web APIs with Protocol Buffers in Swift at iOSConType-safe Web APIs with Protocol Buffers in Swift at iOSCon
Type-safe Web APIs with Protocol Buffers in Swift at iOSConYusuke Kita
 

Andere mochten auch (20)

Minimal Cake Pattern in Swift
Minimal Cake Pattern in SwiftMinimal Cake Pattern in Swift
Minimal Cake Pattern in Swift
 
Androidオールスターズ2016 yanzm
Androidオールスターズ2016 yanzmAndroidオールスターズ2016 yanzm
Androidオールスターズ2016 yanzm
 
なるべくコードを書かないAndroid開発
なるべくコードを書かないAndroid開発なるべくコードを書かないAndroid開発
なるべくコードを書かないAndroid開発
 
はじめようlocalization
はじめようlocalizationはじめようlocalization
はじめようlocalization
 
Phantom Type in Scala
Phantom Type in ScalaPhantom Type in Scala
Phantom Type in Scala
 
Advance text rendering in i os
Advance text rendering in i osAdvance text rendering in i os
Advance text rendering in i os
 
Hi performance table views with QuartzCore and CoreText
Hi performance table views with QuartzCore and CoreTextHi performance table views with QuartzCore and CoreText
Hi performance table views with QuartzCore and CoreText
 
日本の祝祭日を計算してカレンダ-に表示するアプリサンプル
日本の祝祭日を計算してカレンダ-に表示するアプリサンプル日本の祝祭日を計算してカレンダ-に表示するアプリサンプル
日本の祝祭日を計算してカレンダ-に表示するアプリサンプル
 
What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...
What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...
What's New in User Notifications Framework - WWDC16. Meetup @Wantedly with 日本...
 
リテラルと型の続きの話 #__swift__
リテラルと型の続きの話 #__swift__リテラルと型の続きの話 #__swift__
リテラルと型の続きの話 #__swift__
 
Swift + GraphQL
Swift + GraphQLSwift + GraphQL
Swift + GraphQL
 
バ、バカな...!ハッカソンの中で成長しているだと...!?
バ、バカな...!ハッカソンの中で成長しているだと...!?バ、バカな...!ハッカソンの中で成長しているだと...!?
バ、バカな...!ハッカソンの中で成長しているだと...!?
 
多人数iOSアプリ開発を考える
多人数iOSアプリ開発を考える多人数iOSアプリ開発を考える
多人数iOSアプリ開発を考える
 
Web エンジニアが postgre sql を選ぶ 3 つの理由
Web エンジニアが postgre sql を選ぶ 3 つの理由Web エンジニアが postgre sql を選ぶ 3 つの理由
Web エンジニアが postgre sql を選ぶ 3 つの理由
 
RxSwift x Realm
RxSwift x RealmRxSwift x Realm
RxSwift x Realm
 
Swift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorp
Swift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorpSwift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorp
Swift 3 で新しくなったところ - 表面から見えにくいところを中心に紹介 #ISAOcorp
 
アメブロの大規模システム刷新と それを支えるSpring
アメブロの大規模システム刷新と それを支えるSpringアメブロの大規模システム刷新と それを支えるSpring
アメブロの大規模システム刷新と それを支えるSpring
 
20170302 tryswift tasting_tests
20170302 tryswift tasting_tests20170302 tryswift tasting_tests
20170302 tryswift tasting_tests
 
Type-safe Web APIs with Protocol Buffers in Swift at iOSCon
Type-safe Web APIs with Protocol Buffers in Swift at iOSConType-safe Web APIs with Protocol Buffers in Swift at iOSCon
Type-safe Web APIs with Protocol Buffers in Swift at iOSCon
 
Vue.js with Go
Vue.js with GoVue.js with Go
Vue.js with Go
 

Ähnlich wie Understanding Phantom Types in Swift

If love is_blind_-_tiffany
If love is_blind_-_tiffanyIf love is_blind_-_tiffany
If love is_blind_-_tiffanytenka
 
Crushing React bugs with Jest and Enzyme
Crushing React bugs with Jest and EnzymeCrushing React bugs with Jest and Enzyme
Crushing React bugs with Jest and EnzymeAll Things Open
 
Exercícios Netbeans - Vera Cymbron
Exercícios Netbeans - Vera CymbronExercícios Netbeans - Vera Cymbron
Exercícios Netbeans - Vera Cymbroncymbron
 
Advance Java Programs skeleton
Advance Java Programs skeletonAdvance Java Programs skeleton
Advance Java Programs skeletonIram Ramrajkar
 
Node.js basics
Node.js basicsNode.js basics
Node.js basicsBen Lin
 
NodeJs
NodeJsNodeJs
NodeJsdizabl
 
Spring data iii
Spring data iiiSpring data iii
Spring data iii명철 강
 
こわくないよ❤️ Playframeworkソースコードリーディング入門
こわくないよ❤️ Playframeworkソースコードリーディング入門こわくないよ❤️ Playframeworkソースコードリーディング入門
こわくないよ❤️ Playframeworkソースコードリーディング入門tanacasino
 
Workshop 23: ReactJS, React & Redux testing
Workshop 23: ReactJS, React & Redux testingWorkshop 23: ReactJS, React & Redux testing
Workshop 23: ReactJS, React & Redux testingVisual Engineering
 
Construire une application JavaFX 8 avec gradle
Construire une application JavaFX 8 avec gradleConstruire une application JavaFX 8 avec gradle
Construire une application JavaFX 8 avec gradleThierry Wasylczenko
 
Puppet Camp LA 2015: Basic Puppet Module Design (Beginner)
Puppet Camp LA  2015: Basic Puppet Module Design (Beginner)Puppet Camp LA  2015: Basic Puppet Module Design (Beginner)
Puppet Camp LA 2015: Basic Puppet Module Design (Beginner)Puppet
 
Puppetcamp module design talk
Puppetcamp module design talkPuppetcamp module design talk
Puppetcamp module design talkJeremy Kitchen
 
vfsStream - effective filesystem mocking
vfsStream - effective filesystem mocking vfsStream - effective filesystem mocking
vfsStream - effective filesystem mocking Sebastian Marek
 
Railsconf2011 deployment tips_for_slideshare
Railsconf2011 deployment tips_for_slideshareRailsconf2011 deployment tips_for_slideshare
Railsconf2011 deployment tips_for_slidesharetomcopeland
 
"Continuously delivering infrastructure using Terraform and Packer" training ...
"Continuously delivering infrastructure using Terraform and Packer" training ..."Continuously delivering infrastructure using Terraform and Packer" training ...
"Continuously delivering infrastructure using Terraform and Packer" training ...Anton Babenko
 

Ähnlich wie Understanding Phantom Types in Swift (20)

Centos config
Centos configCentos config
Centos config
 
If love is_blind_-_tiffany
If love is_blind_-_tiffanyIf love is_blind_-_tiffany
If love is_blind_-_tiffany
 
Crushing React bugs with Jest and Enzyme
Crushing React bugs with Jest and EnzymeCrushing React bugs with Jest and Enzyme
Crushing React bugs with Jest and Enzyme
 
Exercícios Netbeans - Vera Cymbron
Exercícios Netbeans - Vera CymbronExercícios Netbeans - Vera Cymbron
Exercícios Netbeans - Vera Cymbron
 
Advance Java Programs skeleton
Advance Java Programs skeletonAdvance Java Programs skeleton
Advance Java Programs skeleton
 
Node.js basics
Node.js basicsNode.js basics
Node.js basics
 
NodeJs
NodeJsNodeJs
NodeJs
 
Spring data iii
Spring data iiiSpring data iii
Spring data iii
 
こわくないよ❤️ Playframeworkソースコードリーディング入門
こわくないよ❤️ Playframeworkソースコードリーディング入門こわくないよ❤️ Playframeworkソースコードリーディング入門
こわくないよ❤️ Playframeworkソースコードリーディング入門
 
Workshop 23: ReactJS, React & Redux testing
Workshop 23: ReactJS, React & Redux testingWorkshop 23: ReactJS, React & Redux testing
Workshop 23: ReactJS, React & Redux testing
 
Txjs
TxjsTxjs
Txjs
 
Unittests für Dummies
Unittests für DummiesUnittests für Dummies
Unittests für Dummies
 
Hadoop
HadoopHadoop
Hadoop
 
Construire une application JavaFX 8 avec gradle
Construire une application JavaFX 8 avec gradleConstruire une application JavaFX 8 avec gradle
Construire une application JavaFX 8 avec gradle
 
Puppet Camp LA 2015: Basic Puppet Module Design (Beginner)
Puppet Camp LA  2015: Basic Puppet Module Design (Beginner)Puppet Camp LA  2015: Basic Puppet Module Design (Beginner)
Puppet Camp LA 2015: Basic Puppet Module Design (Beginner)
 
Puppetcamp module design talk
Puppetcamp module design talkPuppetcamp module design talk
Puppetcamp module design talk
 
vfsStream - effective filesystem mocking
vfsStream - effective filesystem mocking vfsStream - effective filesystem mocking
vfsStream - effective filesystem mocking
 
Maze
MazeMaze
Maze
 
Railsconf2011 deployment tips_for_slideshare
Railsconf2011 deployment tips_for_slideshareRailsconf2011 deployment tips_for_slideshare
Railsconf2011 deployment tips_for_slideshare
 
"Continuously delivering infrastructure using Terraform and Packer" training ...
"Continuously delivering infrastructure using Terraform and Packer" training ..."Continuously delivering infrastructure using Terraform and Packer" training ...
"Continuously delivering infrastructure using Terraform and Packer" training ...
 

Mehr von Tomohiro Kumagai

最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow
最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow
最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_growTomohiro Kumagai
 
Swift 所有権 要諦 #ゆるちとせ
Swift 所有権 要諦 #ゆるちとせSwift 所有権 要諦 #ゆるちとせ
Swift 所有権 要諦 #ゆるちとせTomohiro Kumagai
 
_Function Builders in Swift #love_swift
_Function Builders in Swift #love_swift_Function Builders in Swift #love_swift
_Function Builders in Swift #love_swiftTomohiro Kumagai
 
Property Wrappers の特徴を眺める #swiftzoomin
Property Wrappers の特徴を眺める #swiftzoominProperty Wrappers の特徴を眺める #swiftzoomin
Property Wrappers の特徴を眺める #swiftzoominTomohiro Kumagai
 
みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料
みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料
みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料Tomohiro Kumagai
 
みんなで Swift 復習会
GO! in 札幌 – 10th′′
みんなで Swift 復習会
GO! in 札幌 – 10th′′みんなで Swift 復習会
GO! in 札幌 – 10th′′
みんなで Swift 復習会
GO! in 札幌 – 10th′′Tomohiro Kumagai
 
イニシャライザー Part 2.5 #hakataswift
イニシャライザー Part 2.5 #hakataswiftイニシャライザー Part 2.5 #hakataswift
イニシャライザー Part 2.5 #hakataswiftTomohiro Kumagai
 
ニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラ
ニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラ
ニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラTomohiro Kumagai
 
Swift クラスのイニシャライザー #devsap
Swift クラスのイニシャライザー #devsapSwift クラスのイニシャライザー #devsap
Swift クラスのイニシャライザー #devsapTomohiro Kumagai
 
iOSCon 2019 in London #ioscon #love_swift
iOSCon 2019 in London #ioscon #love_swiftiOSCon 2019 in London #ioscon #love_swift
iOSCon 2019 in London #ioscon #love_swiftTomohiro Kumagai
 
Around the 変数 let #love_swift
Around the 変数 let #love_swiftAround the 変数 let #love_swift
Around the 変数 let #love_swiftTomohiro Kumagai
 
もくもく執筆会 #技術同人誌再販Night
もくもく執筆会 #技術同人誌再販Nightもくもく執筆会 #技術同人誌再販Night
もくもく執筆会 #技術同人誌再販NightTomohiro Kumagai
 
みんなで Swift 復習会 GO! in 岩手 – 9th′
みんなで Swift 復習会 GO! in 岩手 – 9th′みんなで Swift 復習会 GO! in 岩手 – 9th′
みんなで Swift 復習会 GO! in 岩手 – 9th′Tomohiro Kumagai
 
macOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswift
macOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswiftmacOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswift
macOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswiftTomohiro Kumagai
 
みんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swift
みんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swiftみんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swift
みんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swiftTomohiro Kumagai
 
Getting Started with Attending iOSCon in London 高画質・追記版 #love_swift #ioscon
Getting Started with Attending iOSCon in London 高画質・追記版 #love_swift #iosconGetting Started with Attending iOSCon in London 高画質・追記版 #love_swift #ioscon
Getting Started with Attending iOSCon in London 高画質・追記版 #love_swift #iosconTomohiro Kumagai
 
みんなで Swift 復習会
GO! in 京都 – 6th′
みんなで Swift 復習会
GO! in 京都 – 6th′みんなで Swift 復習会
GO! in 京都 – 6th′
みんなで Swift 復習会
GO! in 京都 – 6th′Tomohiro Kumagai
 
みんなで Swift 復習会 GO! in 福岡 – 5th′
みんなで Swift 復習会 GO! in 福岡 – 5th′みんなで Swift 復習会 GO! in 福岡 – 5th′
みんなで Swift 復習会 GO! in 福岡 – 5th′Tomohiro Kumagai
 
勉強会の東京外開催の気持ち #yuru_bounen2017
勉強会の東京外開催の気持ち #yuru_bounen2017勉強会の東京外開催の気持ち #yuru_bounen2017
勉強会の東京外開催の気持ち #yuru_bounen2017Tomohiro Kumagai
 
みんなで Swift 復習会 GO! in 福岡・発表資料
みんなで Swift 復習会 GO! in 福岡・発表資料みんなで Swift 復習会 GO! in 福岡・発表資料
みんなで Swift 復習会 GO! in 福岡・発表資料Tomohiro Kumagai
 

Mehr von Tomohiro Kumagai (20)

最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow
最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow
最近気づいた勉強法 — 勉強会開催の習慣化 #yumemi_grow
 
Swift 所有権 要諦 #ゆるちとせ
Swift 所有権 要諦 #ゆるちとせSwift 所有権 要諦 #ゆるちとせ
Swift 所有権 要諦 #ゆるちとせ
 
_Function Builders in Swift #love_swift
_Function Builders in Swift #love_swift_Function Builders in Swift #love_swift
_Function Builders in Swift #love_swift
 
Property Wrappers の特徴を眺める #swiftzoomin
Property Wrappers の特徴を眺める #swiftzoominProperty Wrappers の特徴を眺める #swiftzoomin
Property Wrappers の特徴を眺める #swiftzoomin
 
みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料
みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料
みんなで Swift 復習会 GO! in "Swift Days Fukuoka" – 12nd′ オープニング&資料
 
みんなで Swift 復習会
GO! in 札幌 – 10th′′
みんなで Swift 復習会
GO! in 札幌 – 10th′′みんなで Swift 復習会
GO! in 札幌 – 10th′′
みんなで Swift 復習会
GO! in 札幌 – 10th′′
 
イニシャライザー Part 2.5 #hakataswift
イニシャライザー Part 2.5 #hakataswiftイニシャライザー Part 2.5 #hakataswift
イニシャライザー Part 2.5 #hakataswift
 
ニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラ
ニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラ
ニコニコ超会議・文化の交差点 #techpub #ニコニコ超会議 #さくらシンデレラ
 
Swift クラスのイニシャライザー #devsap
Swift クラスのイニシャライザー #devsapSwift クラスのイニシャライザー #devsap
Swift クラスのイニシャライザー #devsap
 
iOSCon 2019 in London #ioscon #love_swift
iOSCon 2019 in London #ioscon #love_swiftiOSCon 2019 in London #ioscon #love_swift
iOSCon 2019 in London #ioscon #love_swift
 
Around the 変数 let #love_swift
Around the 変数 let #love_swiftAround the 変数 let #love_swift
Around the 変数 let #love_swift
 
もくもく執筆会 #技術同人誌再販Night
もくもく執筆会 #技術同人誌再販Nightもくもく執筆会 #技術同人誌再販Night
もくもく執筆会 #技術同人誌再販Night
 
みんなで Swift 復習会 GO! in 岩手 – 9th′
みんなで Swift 復習会 GO! in 岩手 – 9th′みんなで Swift 復習会 GO! in 岩手 – 9th′
みんなで Swift 復習会 GO! in 岩手 – 9th′
 
macOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswift
macOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswiftmacOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswift
macOS アプリで Swift Package Manager を使ってみる #love_swift #hakataswift
 
みんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swift
みんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swiftみんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swift
みんなで Swift 復習会 GO! in 福岡 – 8th′ #minna_de_swift
 
Getting Started with Attending iOSCon in London 高画質・追記版 #love_swift #ioscon
Getting Started with Attending iOSCon in London 高画質・追記版 #love_swift #iosconGetting Started with Attending iOSCon in London 高画質・追記版 #love_swift #ioscon
Getting Started with Attending iOSCon in London 高画質・追記版 #love_swift #ioscon
 
みんなで Swift 復習会
GO! in 京都 – 6th′
みんなで Swift 復習会
GO! in 京都 – 6th′みんなで Swift 復習会
GO! in 京都 – 6th′
みんなで Swift 復習会
GO! in 京都 – 6th′
 
みんなで Swift 復習会 GO! in 福岡 – 5th′
みんなで Swift 復習会 GO! in 福岡 – 5th′みんなで Swift 復習会 GO! in 福岡 – 5th′
みんなで Swift 復習会 GO! in 福岡 – 5th′
 
勉強会の東京外開催の気持ち #yuru_bounen2017
勉強会の東京外開催の気持ち #yuru_bounen2017勉強会の東京外開催の気持ち #yuru_bounen2017
勉強会の東京外開催の気持ち #yuru_bounen2017
 
みんなで Swift 復習会 GO! in 福岡・発表資料
みんなで Swift 復習会 GO! in 福岡・発表資料みんなで Swift 復習会 GO! in 福岡・発表資料
みんなで Swift 復習会 GO! in 福岡・発表資料
 

Kürzlich hochgeladen

Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...
Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...
Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...kellynguyen01
 
Optimizing AI for immediate response in Smart CCTV
Optimizing AI for immediate response in Smart CCTVOptimizing AI for immediate response in Smart CCTV
Optimizing AI for immediate response in Smart CCTVshikhaohhpro
 
How To Troubleshoot Collaboration Apps for the Modern Connected Worker
How To Troubleshoot Collaboration Apps for the Modern Connected WorkerHow To Troubleshoot Collaboration Apps for the Modern Connected Worker
How To Troubleshoot Collaboration Apps for the Modern Connected WorkerThousandEyes
 
Right Money Management App For Your Financial Goals
Right Money Management App For Your Financial GoalsRight Money Management App For Your Financial Goals
Right Money Management App For Your Financial GoalsJhone kinadey
 
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...OnePlan Solutions
 
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...panagenda
 
Software Quality Assurance Interview Questions
Software Quality Assurance Interview QuestionsSoftware Quality Assurance Interview Questions
Software Quality Assurance Interview QuestionsArshad QA
 
CALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female service
CALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female serviceCALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female service
CALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female serviceanilsa9823
 
+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...
+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...
+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...Health
 
Unveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
Unveiling the Tech Salsa of LAMs with Janus in Real-Time ApplicationsUnveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
Unveiling the Tech Salsa of LAMs with Janus in Real-Time ApplicationsAlberto González Trastoy
 
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...Steffen Staab
 
HR Software Buyers Guide in 2024 - HRSoftware.com
HR Software Buyers Guide in 2024 - HRSoftware.comHR Software Buyers Guide in 2024 - HRSoftware.com
HR Software Buyers Guide in 2024 - HRSoftware.comFatema Valibhai
 
A Secure and Reliable Document Management System is Essential.docx
A Secure and Reliable Document Management System is Essential.docxA Secure and Reliable Document Management System is Essential.docx
A Secure and Reliable Document Management System is Essential.docxComplianceQuest1
 
CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online ☂️
CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online  ☂️CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online  ☂️
CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online ☂️anilsa9823
 
Diamond Application Development Crafting Solutions with Precision
Diamond Application Development Crafting Solutions with PrecisionDiamond Application Development Crafting Solutions with Precision
Diamond Application Development Crafting Solutions with PrecisionSolGuruz
 
Hand gesture recognition PROJECT PPT.pptx
Hand gesture recognition PROJECT PPT.pptxHand gesture recognition PROJECT PPT.pptx
Hand gesture recognition PROJECT PPT.pptxbodapatigopi8531
 
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdfLearn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdfkalichargn70th171
 
Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...
Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...
Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...harshavardhanraghave
 

Kürzlich hochgeladen (20)

Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...
Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...
Short Story: Unveiling the Reasoning Abilities of Large Language Models by Ke...
 
Optimizing AI for immediate response in Smart CCTV
Optimizing AI for immediate response in Smart CCTVOptimizing AI for immediate response in Smart CCTV
Optimizing AI for immediate response in Smart CCTV
 
How To Troubleshoot Collaboration Apps for the Modern Connected Worker
How To Troubleshoot Collaboration Apps for the Modern Connected WorkerHow To Troubleshoot Collaboration Apps for the Modern Connected Worker
How To Troubleshoot Collaboration Apps for the Modern Connected Worker
 
Right Money Management App For Your Financial Goals
Right Money Management App For Your Financial GoalsRight Money Management App For Your Financial Goals
Right Money Management App For Your Financial Goals
 
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
Tech Tuesday-Harness the Power of Effective Resource Planning with OnePlan’s ...
 
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
W01_panagenda_Navigating-the-Future-with-The-Hitchhikers-Guide-to-Notes-and-D...
 
Software Quality Assurance Interview Questions
Software Quality Assurance Interview QuestionsSoftware Quality Assurance Interview Questions
Software Quality Assurance Interview Questions
 
CALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female service
CALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female serviceCALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female service
CALL ON ➥8923113531 🔝Call Girls Badshah Nagar Lucknow best Female service
 
+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...
+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...
+971565801893>>SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHAB...
 
Microsoft AI Transformation Partner Playbook.pdf
Microsoft AI Transformation Partner Playbook.pdfMicrosoft AI Transformation Partner Playbook.pdf
Microsoft AI Transformation Partner Playbook.pdf
 
Unveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
Unveiling the Tech Salsa of LAMs with Janus in Real-Time ApplicationsUnveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
Unveiling the Tech Salsa of LAMs with Janus in Real-Time Applications
 
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
 
HR Software Buyers Guide in 2024 - HRSoftware.com
HR Software Buyers Guide in 2024 - HRSoftware.comHR Software Buyers Guide in 2024 - HRSoftware.com
HR Software Buyers Guide in 2024 - HRSoftware.com
 
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICECHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
 
A Secure and Reliable Document Management System is Essential.docx
A Secure and Reliable Document Management System is Essential.docxA Secure and Reliable Document Management System is Essential.docx
A Secure and Reliable Document Management System is Essential.docx
 
CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online ☂️
CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online  ☂️CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online  ☂️
CALL ON ➥8923113531 🔝Call Girls Kakori Lucknow best sexual service Online ☂️
 
Diamond Application Development Crafting Solutions with Precision
Diamond Application Development Crafting Solutions with PrecisionDiamond Application Development Crafting Solutions with Precision
Diamond Application Development Crafting Solutions with Precision
 
Hand gesture recognition PROJECT PPT.pptx
Hand gesture recognition PROJECT PPT.pptxHand gesture recognition PROJECT PPT.pptx
Hand gesture recognition PROJECT PPT.pptx
 
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdfLearn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
 
Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...
Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...
Reassessing the Bedrock of Clinical Function Models: An Examination of Large ...
 

Understanding Phantom Types in Swift

  • 1.
  • 2.
  • 4.
  • 6.
  • 7.
  • 8.
  • 9. class HogeOperation { private(set) var isPrepared = false func prepare() { guard !isPrepared else { fatalError("prepare を複数回呼ばないこと") } isPrepared = true } }
  • 10. // Init 状態の HogeOperation を生成 let operation = HogeOperation<Init>() // 最初は prepared を呼べて準備完了したものを取得可能 let preparedOp = operation.prepared() // 準備が終われば prepared はビルドエラーで実行不可 preparedOp.prepared()
  • 11.
  • 12. // これで "操作状態を表現する型" を表現 protocol OperationState {} // 操作状態ごとにクラスを定義 class Init: OperationState {} class Prepared: OperationState {}
  • 13. // 型パラメーターで型に状態を付与 class HogeOperation<State: OperationState> { /* 今回は内部で、 型パラメーターを使わないのがポイント */ }
  • 14. extension HogeOperation where State: Init { // 準備を実行し、準備完了状態のインスタンスを返す func prepared() -> HogeOperation<Prepared> {…} } extension HogeOperation where State: Prepared { // 目的の操作を実行する func execute() {…} }
  • 15.
  • 16. let operation = HogeOperation<Init>() // Init 状態では、まだ execute は存在しない operation.execute() // prepared を呼ぶことで Prepared 状態のものを取得 let preparedOp = operation.prepared() // Prepared 状態には、もう prepared は存在しない preparedOp.prepared()
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22. let operation = HogeOperation<Init>() // HogeOperation<Init> 型だから prepared が呼べる let preparedOp: HogeOperation<Prepared>() = operation.prepared() // HogeOperation<Prepared> 型だから execute が呼べる preparedOp.execute() // Init クラスや Prepared クラスを、実行時には使わない // ビルドの段階で、もう役目が済んでいる
  • 23.
  • 24. let operation = HogeOperation<Init>() let preparedOp = operation.prepared() let type1 = type(of: operation) let type2 = type(of: preparedOp) type1 == type2 // false
  • 25. // 型パラメーターで型に状態を付与 class HogeOperation<State: OperationState> { /* 内部では、型パラメーターを使っていない 型の在り方を説明するためだけに使っている */
  • 26.
  • 27. /// Phantom Type に出逢う前の認識 // Array はテンプレート的なもので… struct Array<Element> { } // 型パラメーターによって、異なる型になる let values: Array<Int> = Array<String>()
  • 28.
  • 29. // protocol OperationState {} // class Init: OperationState {} // class Prepared: OperationState {}
  • 30. class Operation { fileprivate var data: OperationData fileprivate init(data: OperationData) { self.data = data } func mob() {} }
  • 31. class OperationInit: Operation { convenience init() {…} func prepared() -> OperationPrepared {…} } class OperationPrepared: Operation { func execute() {…} }
  • 32. let operation = OperationInit() let preparedOp = operation.prepared() preparedOp.execute()
  • 33.
  • 34. struct OperationInit { fileprivate var data: OperationData fileprivate init(data: OperationData) {…} // 共通機能 func mob() {} // 固有の機能 init() {…} func prepared() -> OperationPrepared {…} }
  • 35. struct OperationPrepared { fileprivate var data: OperationData fileprivate init(data: OperationData) {…} // 共通機能 func mob() {} // 固有の機能 func execute() {…} }
  • 36. let operation = OperationInit() let preparedOp = operation.prepared() preparedOp.execute()
  • 37. protocol Operation {} struct OperationInit: Operation { … } struct OperationPrepared: Operation { … }
  • 38.
  • 39. struct Operation { struct Init { … } struct Prepared { … } }
  • 40. let operation = Operation.Init() let preparedOp = operation.prepared() preparedOp.execute()
  • 41.
  • 42. class Operation { fileprivate var data: OperationData fileprivate init(data: OperationData) { self.data = data } func mob() {} }
  • 43. extension Operation { class Init: Operation { … } class Prepared: Operation { … } }
  • 44. let operation = Operation.Init() let preparedOp = operation.prepared() preparedOp.execute()
  • 45.
  • 46.
  • 47.
  • 48.
  • 49. class HogeOperation<State: OperationState> { func mob() {…} } extension HogeOperation where State: Init { func prepared() -> HogeOperation<Prepared> {…} } extension HogeOperation where State: Prepared { func execute() {…} }
  • 50. let operation = HogeOperation<Init>() operation.execute()
  • 51. let operation = OperationInit() operation.execute()
  • 52.
  • 54. protocol Operation {} class HogeOperation<State: OperationState>: Operation { } var op: Operation op = HogeOperation<Init>() op = (op as! HogeOperation<Init>).prepared() op = (op as! HogeOperation<Prepared>).execute()
  • 55.
  • 56. class Driver { init(channel: Int? = nil, volume: Int? = nil, pan: Int? = nil, format: Format? = nil, route: Route? = nil) { } } // 設定項目に何があるかや、設定順番に気を使う let driver = Driver(volume: 10, format: ulaw, route: .speaker)
  • 57. // 本体のクラスを Phantom Type で定義して… class Driver<State> where State: AudioState { } // 準備が整ったときの機能を実装し… extension Driver where State: Ready { func start() { … } }
  • 58. // 初期化中にできることを規定すると… extension Driver where State: Setup { func prepared() -> Driver<Ready> { … } func set(channel: Int) -> Driver { return self } func set(volume: Int) -> Driver { return self } func set(pan: Int) -> Driver { return self } func set(format: Format) -> Driver { return self } func set(route: Route) -> Driver { return self } }
  • 59. // 初期設定では、順番を気にせず設定できる・補完が効く let driver = Driver<Setup>() .set(format: ulaw) .set(volume: 10) .set(route: .speaker) .prepared() // ここで Driver<Ready>() を返す // 設定完了を宣言 (prepared) して、使い始める driver.start()
  • 60. let driver = Driver<Setup>() .format // → Driver<FormatSetup> .set(sampleRate: 44100) .set(channelsPerFrame: 2) .general // → Driver<GeneralSetup> .set(volume: 10) .set(route: .speaker) .prepared() // → Driver<Ready>
  • 61. let driver = Driver.setup() // → DriverSetup .format // → FormatSetup .set(sampleRate: 44100) .set(channelsPerFrame: 2) .general // → AudioSetup .set(volume: 10) .set(route: .speaker) .prepared() // → Driver
  • 62.
  • 63. // 設定項目を、初期値を持った構造体で用意して… struct Description { var channel: Int = default var volume: Int = default var pan: Int = default var format: Format = default var route: Route = default }
  • 64. let description = Description() description.format.sampleRate = 44100 description.format.channelsPerFrame = 2 description.volume = 10 description.route = .speaker
  • 65. // Driver は Description で初期化するようにして… class Driver { init(description: Description) { … } } // 設定項目を渡して、初期化を完成する let driver = Driver(description: description)
  • 66.
  • 67.
  • 68. class Controller { var environment: Environment<Neutral> }
  • 69. struct Environment<State> { fileprivate(set) var platform: Platform fileprivate(set) var version: Double func startEditing() -> Environment<Editing> { return Environment<Editing>( platform: platform, version: version) } }
  • 70. extension Environment where State: Editing { mutating func set(platform: Platform) { … } mutating func set(version: Double) { … } func endEditing() -> Environment<Neutral> { return Environment<Neutral>( platform: platform, version: version) } }
  • 71. func update() { // 編集状態で取り出さないと、書き込めない var environment = self.environment.startEditing() environment.set(platform: .macOS) environment.set(version: Platform.macOS.latest) // ローカルで編集を終了したら、書き戻す self.environment = environment.endEditing() }
  • 72.
  • 73. extension Environment where State: Editing { var platform: Platform var version: Double // 同じ内容の、別インスタンスを作り直している func endEditing() -> Environment<Neutral> { return Environment<Neutral>( platform: platform, version: version) }
  • 74. extension Environment where State: Editing { // 内容を原始的にコピーしないといけないとき func endEditing() -> Environment<Neutral> { var result = Environment<Neutral>() result.platform = platform result.version = version return result }
  • 75.
  • 76. struct Environment<State> { fileprivate(set) var platform: Platform fileprivate(set) var version: Double } extension Environment { fileprivate init<S>(takeover: Environment<S>) { platform = takeover.platform version = takeover.version } }
  • 77. extension Environment where State: Editing { func endEditing() -> Environment<Neutral> { return Environment<Neutral>(takeover: self) } }
  • 78.
  • 79. struct Environment<State> { // データをここで集中管理する fileprivate struct Context { var platform: Platform var version: Double } // これだけを引き継げば済む状況を作る fileprivate var _context: Context }
  • 80. extension Environment { fileprivate init(context: Context) { _context = context } }
  • 81. extension Environment where State: Editing { func endEditing() -> Environment<Neutral> { return Environment<Neutral>(context: _context) } }
  • 82. extension Environment { var platform: Platform { get { _context.platform } set { _context.platform = newValue } } var version: Double { get { _context.version } set { _context.version = newValue } }
  • 83.
  • 84. extension Environment where State: Editing { func endEditing() -> Environment<Neutral> { // 準備不要で、いきなりビットキャスト可能 return unsafeBitCast(self, to: Environment<Neutral>.self) } }
  • 85. extension Environment { fileprivate init<S>(takeover: Environment<S>) { self = unsafeBitCast(takeover, to: Environment.self) } }
  • 86. let sub: Base = Sub() let base: Base = Base() // 実体が Sub なので、全ての機能が使える let obj: Sub = unsafeBitCast(sub, to: Sub.self) // 実体が Base なので、Sub の機能を使うとクラッシュする let obj: Sub = unsafeBitCast(base, to: Sub.self)
  • 87.
  • 88.
  • 89. class Test: OperationState {} extension HogeOperation where State: Test { func testSomething() {…} } extension HogeOperation where State: Init { func testing() -> HogeOperation<Test> {…} }
  • 90.
  • 91. // Test 状態を Prepared から継承させれば… class Test: Prepared {} // Test には Prepared の機能も備わる extension HogeOperation where State: Prepared { func execute() {…} } extension HogeOperation where State: Test { func testSomething() {…} }