Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

よくある問題

💡 お知らせ: このドキュメントはAIによって翻訳されています。表現に違和感がある場合は、原文(英語)を参照するか、翻訳にご協力ください。

ToString is not defined on ‘a’

次のプログラムを考えます:

def main(): Unit \ IO =
    let l = Nil;
    println(l)

Flix コンパイラは次のように報告します:

❌ -- Type Error ---------------------

>> ToString is not defined on a. [...]

3 |     println(l)
        ^^^^^^^^^^
        missing ToString instance

問題は、空のリストが任意の a に対する多相型 List[a] を持つことです。このため、Flix は適切な ToString トレイトのインスタンスを選択できません。

解決策は、空のリストの型を指定することです。例えば、次のように書けます:

def main(): Unit \ IO =
    let l: List[Int32] = Nil;
    println(l)

これで問題は解決します。具体的な型 List[Int32] に対しては、Flix が ToString トレイトのインスタンスを見つけられるからです。

レコードと複雑なインスタンス

次のプログラムを考えます:

instance Eq[{fstName = String, lstName = String}]

Flix コンパイラは次のように報告します:

❌ -- Instance Error --------------------------------------------------

>> Complex instance type '{ fstName = String, lstName = String }' in 'Eq'.

1 | instance Eq[{fstName = String, lstName = String}]
             ^^
             complex instance type

これは、少なくとも現時点では、レコード(や Datalog スキーマの行)に対してトレイトインスタンスを定義できないためです。この制限は将来変わるかもしれません。それまでは、レコードを代数的データ型で包む必要があります。例えば:

enum Person({fstName = String, lstName = String})

このようにすれば、Person 型に対して Eq を実装できます:

instance Eq[Person] {
    pub def eq(x: Person, y: Person): Bool =
        let Person(r1) = x;
        let Person(r2) = y;
        r1#fstName == r2#fstName and r1#lstName == r2#lstName
}

Expected kind ‘Bool or Effect’ here, but kind ‘Type’ is used

次のプログラムを考えます:

enum A[a, b, ef] {
    case A(a -> b \ ef)
}

Flix コンパイラは次のように報告します:

❌ -- Kind Error -----------------------------------------------

>> Expected kind 'Bool or Effect' here, but kind 'Type' is used.

2 |     case A(a -> b \ ef)
                        ^^
                        unexpected kind.

Expected kind: Bool or Effect
Actual kind:   Type

これは、Flix が注釈のない型変数はすべてカインド Type を持つと仮定するためです。しかし上記の例では、ab はカインド Type を持つべきですが、ef はカインド Bool を持つべきです。次のように明示的に指定できます:

enum A[a: Type, b: Type, ef: Bool] {
    case A(a -> b \ ef)
}