Scala → Python3比較表 ①クラスと関数定義

2019-03-21

はじめに

私はScalaが大好きです。今まで困ったらまずScalaでコードを書いてました。

が、今の時代pythonの勢力が強く、学ばないと取り残されてしまいそうです。

そのため、Scala目線でのScala→Python3対応表を作成し、ScalaからPython3へのを容易にしたく思います!

実践!

教頭Class/先生Class/学生Classを定義して比べてみましょう。

条件は下記となります。
教頭は一人です(Singleton)。教頭は先生を複数管理し、先生/学生の名簿を持つことができます。
先生は学生を複数管理し、学生の名簿を持つことができます。名前と性別があります。
学生は名前と性別があります。
先生も学生も呼ぶ時は性別に応じて”Mr/Ms”をつけなければなりません。

Scala

trait Sex
case class Man() extends Sex
case class Woman() extends Sex

trait Honorific{
    val name: String
    val sex: Sex
    def call = {
        sex match{
            case Man() => s"Mr.$name"
            case Woman() => s"Ms.$name"
        }
    }
}

case class Student(val name: String, val sex:Sex) extends Honorific

case class Teacher(val name: String, val sex: Sex, val students: List[Student]) extends Honorific{
    def call_students = students.foreach(x => println(x.call))
}

object VicePrincipal{
    val teachers = List(
        Teacher("aikawa", Man(), List(Student("ogawa", Woman()))),
        Teacher("kagawa", Woman(), List(Student("koyama", Man()))))
    def call_teachers = teachers.foreach(x => println(x.call))
}

Scalaは型(クラス)定義と関数定義が非常に強力で、かつ簡素でわかりやすいです。

trait/case class/objectを使えば基本的に何でもできます。
入れ物をどんどん作っていく流れで、コンパイル通れば実行時にバグはほとんど起きません

Python

from dataclasses import dataclass
from typing import List

class Honorific:
    @staticmethod
    def add(name, sex):
        if sex == "man":
            return f"Mr.{name}"
        else:
            return f"Ms.{name}"


@dataclass(frozen=True)
class Student:
    name: str
    sex: str
    def call(self):
        print(Honorific.add(self.name, self.sex))


@dataclass(frozen=True)
class Teacher:
    name: str
    sex: set
    students: List[str]
    def call(self):
        print(Honorific.add(self.name, self.sex))
    def call_students(self):
        list(map(lambda x:x.call(), self.students))

class VicePrincipal:
    teachers = [Teacher("aikawa","man",{Student("ogawa","woman")}), Teacher("kagawa","woman",{Student("koyama","man")})]
    @staticmethod
    def call_teachers():
        list(map(lambda x:x.call(), teachers))

Pythonは型クラスや抽象クラスのに非常に弱く、いちいちimportしないといけないのがめんどくさい。

あとList処理に弱く、mapやlamda等専用の関数を用いなければならないことがすごく憂鬱。

まとめ

PythonでできることはScalaでできるけど、

ScalaでできることはPythonでできない。

特に型クラス定義、list処理でPythonはScalaに遠く及ばない。

大規模でマルチスレッド・スケーラブル・ロバスト性が求められるのはScala

それ以外はPythonで書くのが良さそう。

Python, Scala

Posted by RV