Доступ к членам класса Fantom из функции-члена в конструкторе it-block?

Если я определю этот класс Fantom

const class Mixed
{
  const Int whole
  const Int numerator
  const Int denominator

  const | -> Int[]| convertToFrac

  new make( |This| func ) { func( this ) }
}

И я хочу создать экземпляр, определяющий функцию convertToFrac, например:

class Example
{
  Void main( Str args )
  {
    mixed := Mixed {
      whole = 2
      numerator = 3
      denominator = 8
      convertToFrac = |->Int[]| {
        return [ whole * denominator + numerator, denominator ]
      }
    }
  }
}

Компилятор жалуется, говоря:

  • Unknown variable 'numerator'
  • Unknown variable 'denominator'
  • Unknown variable 'whole'

Есть ли способ ссылаться на объект "mixed", создаваемый из функции "convertToFrac", также определяемой, без передачи объекта "mixed" в качестве параметра функции?

Если я добавлю каждую переменную с "смешанным", например, так:

return [ mixed.whole * mixed.denominator + mixed.numerator, mixed.denominator ]

Компилятор жалуется: Unknown variable 'mixed',

С помощью this.whole не имеет смысла, так как относится к классу Example. С помощью it.whole не имеет смысла, так как это относится к функции.

Кто-нибудь может предложить, пожалуйста, способ доступа к "смешанному" объекту из функции "convertToFrac"?

1 ответ

Решение

Как вы правильно оценили, проблема в том, что вы используете it-block внутри it-blockи потому что вы используете неявный it (т.е. у вас нет it определители) существует путаница относительно того, на что ссылаются.

Я выпишу it отборочные лонг хэнд, так что вы можете увидеть, что происходит:

mixed := Mixed {
    // 'it' is the Mixed instance
    it.whole = 2
    it.numerator = 3
    it.denominator = 8

    it.convertToFrac = |->Int[]| {
        // 'it' is now the func param

        // 'it.whole' doesn't exist, because there is no func param
        return [ it.whole * it.denominator + it.numerator, it.denominator ]
    }
}

Ваша идея использования mixed переменный квалификатор был хорошим, но, к сожалению, при обработке ctor mixed переменная еще не была создана, поэтому на нее нельзя ссылаться.

Но вы можете создать свой собственный mixed переменная в it-блоке, а следующая компилируется и работает довольно счастливо:

mixed := Mixed {
    // 'mixed' doesn't exist here yet, because we're still creating a value to assign to it
    it.whole = 2
    it.numerator = 3
    it.denominator = 8

    // assign `it` to our own `mixed` variable
    mixed := it
    it.convertToFrac = |->Int[]| {
        // use our own `mixed` variable
        return [ mixed.whole * mixed.denominator + mixed.numerator, mixed.denominator ]
    }
}
Другие вопросы по тегам