Різниця між цим та "Я" в анотаціях самовведення?


134

У різній літературі Scala я бачу деякі анотації самовведення, використовуючи "це", а інші використовуючи "self":

trait A { this: B => ... }
trait A { self: B => ... }

Чи є реальна різниця між використанням "цього" чи "самості"? Чи має значення взагалі, яке ім’я ви використовуєте? Це так само справедливо?

trait A { foo: B => ... }

Відповіді:


181

Усі три форми є дійсними та мають ефект, який Bвважається типом thisкласу A.

Перші два варіанти

trait A { self: B => ... }
trait A { foo: B => ... }

ввести self(відповідно foo) як псевдонім для thisознаки A. Це корисно для доступу до thisпосилань із внутрішнього класу. Тобто ви могли б використовувати selfзамість того, A.thisщоб отримати доступ до thisпосилання ознаки Aз класу, вкладеного в неї. Приклад:

class MyFrame extends JFrame { frame =>    
  getContentPane().add( new JButton( "Hide" ) {
    addActionListener( new ActionListener {
      def actionPerformed( e: ActionEvent ) {
        // this.setVisible( false ) --> shadowed by JButton!
        frame.setVisible( false )
      }
    })
  })
}

Третій варіант,

trait A { this: B => ... }

не вводить псевдонім для this; він просто встановлює тип самості.


Те, як я дивлюся на тип власного типу, полягає в тому, що ознака заявила себе за прийняття певного типу та повернення кодового блоку, наприклад foo: B => {...}. Тепер ці кучері, звичайно, опущені. Цікаво побачити, що ви можете використовувати назву об’єкта замість "цього" всередині будь-якої області коду, хоча [щось ми робимо весь час у javascript]
Ustaman Sangat

4
@Martin Odersky Чи можна додати обмеження на дві чи більше рис, щось на кшталт trait A { self: B, C => ... }?
Дмитро Беспалов

13
@DmitryBespalov: Так, ви можете використовувати withключове слово в анотації самовведення . Наприкладtrait A { self: B with C => ... }
Дейв

btw ви також можете зробити _: B =>для справи, що не є псевдонімом, для простоти
Creos

17

Є різниця в тому, що thisзавжди посилається на об'єкт, визначений найпотаємнішим шаблоном.

Вираз thisможе відображатися в частині висловлювань шаблону або типу сполуки. Це означає, що об'єкт визначається самим внутрішнім шаблоном або типом сполуки, що додає посилання. Якщо це складний тип, то тип такого thisтипу з'єднання. Якщо шаблон класу або об'єкта визначення з простим ім'ям C , тип це те ж саме , як тип C . this. (Scala Ref. §6.5)

Отже, якщо ви називаєте свій тип власного типу foo, ви все ще можете посилатися на нього як this(якщо, звичайно, ви не знаходитесь у внутрішньому шаблоні, в цьому випадку thisбуде посилатися на визначений ним об'єкт - і якщо ви не надасте внутрішній введіть однотипну шаблону), але, очевидно, не навпаки.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.