Skip to content

Instantly share code, notes, and snippets.

@eiel
Last active April 23, 2018 16:10
Show Gist options
  • Save eiel/900fd6435519f71e2327379a4339a6f9 to your computer and use it in GitHub Desktop.
Save eiel/900fd6435519f71e2327379a4339a6f9 to your computer and use it in GitHub Desktop.
多相確認
# 構造体定義
defmodule Cat do
defstruct [:name]
end
defmodule Dog do
defstruct [:name]
end
# インターフェイス定義
defprotocol Sayable do
def say(_, message)
end
# 実装
defimpl Sayable, for: Cat do
def say(%{name: name}, message), do: IO.puts("#{name}: #{message}だにゃー")
end
defimpl Sayable, for: Dog do
def say(%{name: name}, message), do: IO.puts("#{name}: #{message}だわん")
end
defmodule Main do
# 多相性確認
def run(sayable) do
# 普通にかくと
# Sayable.say(sayable, "おはよう")
import Sayable
sayable |> say("おはよう") # $sayable->say("おはよう") によく似てますね
# import しない場合:
# sayable |> Sayable.say("おはよう")
end
# エントリーポイント
def main do
run(%Cat{name: "たま"})
run(%Dog{name: "ぽち"})
end
end
# エントリーポイント呼び出し
Main.main
"""
# 実行結果
たま: おはようだにゃー
ぽち: おはようだわん
"""
package main
import "fmt"
// 構造体定義
type Cat struct {name string}
type Dog struct {name string}
// インターフェイス定義
type Sayable interface {
Say(string)
}
// 実装
func (x Cat) Say(message string) {
fmt.Printf("%v: %vだにゃー\n", x.name, message)
}
func (x Dog) Say(message string) {
fmt.Printf("%v: %vだわん\n", x.name, message)
}
// 多相性確認
func run(sayable Sayable) {
sayable.Say("おはよう")
}
// エントリーポイント
func main() {
run(Cat{"たま"})
run(Dog{"ぽち"})
}
import Text.Printf
-- 構造体定義
newtype Cat = Cat String
newtype Dog = Dog String
-- インターフェイス定義
class Sayable a where
say :: String -> a -> IO () -- 実装を決める型はどこにあっても良い。今回は二番目の引数に
-- 実装
instance Sayable Cat where
say message (Cat name) = printf "%s: %sだにゃー\n" name message
instance Sayable Dog where
say message (Dog name) = printf "%s: %sだにゃー\n" name message
-- 多相性確認
run :: (Sayable a) => a -> IO ()
run = say "おはよう"
-- エントリーポイント
main = do
run . Cat $ "たま"
run . Dog $ "ぽち"
// ネタです
// 実装
const SayableForCat = ({
say(message) {
console.log(`${this.name}: ${message}だにゃー`)
}
})
const SayableForDog = ({
say(message) {
console.log(`${this.name}: ${message}だわん`)
}
})
// 実装の注入
const Cat = (sayable) => ({
...sayable,
...SayableForCat,
})
const Dog = (sayable) => ({
...sayable,
...SayableForDog,
})
// 多相性の確認
const run = (sayable) => sayable.say("おはよう")
run(Cat({name: "たま"}))
run(Dog({name: "ぽち"}))
<?php
// インターフェイス定義
interface Sayable {
public function say($message);
}
// 構造体定義 & 実装
class Cat implements Sayable {
private $name;
function __construct(string $name) {
$this->name = $name;
}
public function say($message) {
echo "{$this->name}: ${message}だにゃー\n";
}
}
class Dog implements Sayable {
private $name;
function __construct(string $name) {
$this->name = $name;
}
public function say($message) {
echo "{$this->name}: ${message}だわん\n";
}
}
// 多相性確認
function run(Sayable $sayable) {
$sayable->say("おはよう");
}
run(new Cat("たま"));
run(new Dog("ぽち"));
// 構造体定義
struct Cat {
name: String,
}
struct Dog {
name: String,
}
// インターフェイス定義
trait Sayable {
fn say(&self, &str);
}
// 実装
impl Sayable for Cat {
fn say(&self, message: &str) {
println!("{}: {}だにゃー", self.name, message)
}
}
impl Sayable for Dog {
fn say(&self, message: &str) {
println!("{}: {}だわん", self.name, message)
}
}
// 多相性確認
fn run(sayable: &Sayable) {
sayable.say("おはよう")
}
// エントリーポイント
fn main() {
run(&Cat{name: "たま".to_string()});
run(&Dog{name: "ぽち".to_string()})
}
// 構造体定義
struct Cat {
var name: String
}
struct Dog {
var name: String
}
// インターフェイス定義
protocol Sayable {
func say(_ message: String)
}
// 実装
extension Cat: Sayable {
func say(_ message: String) {
print("\(self.name): \(message)だにゃー")
}
}
extension Dog: Sayable {
func say(_ message: String) {
print("\(self.name): \(message)だわん")
}
}
// 多相性確認
func run(_ sayable: Sayable) {
sayable.say("おはよう")
}
run(Cat(name: "たま"))
run(Dog(name: "ぽち"))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment