簡體   English   中英

在coffeescript繼承鏈中注入一個新類

[英]Injecting a new class into the coffeescript inheritance chain

我有三個coffeescript類,設置如下:

class A
class C extends A
class B

這樣原型鏈看起來像這樣:

A -> C
B

我需要原型鏈看起來像這樣:

A -> B -> C

問題在於我無法觸及A和C的定義。

我想做的是創建一個可以像這樣調用的注入函數:

inject B, C

在A之前將B注入C的原型鏈中,然后將B的原型鏈設置為注入之前的任何C。

我認為這很簡單,就像

C extends (B extends C.prototype)

但不幸的是,由於coffeescript所做的所有原型/ __ super__魔術,事情並不那么簡單。 有沒有人知道如何注入原型鏈,這基本上就像你說class C extends Bclass B extends A首先class B extends A

非常感謝。

澄清:以下代碼不起作用,因為屬性無法復制。

class A
  foo: 1
class B
  bar: 2
class C extends A
  baz: 3

B extends A
C extends B

c = new C
console.log c.foo
console.log c.bar
console.log c.baz

[ 更新:我原來回答說C extends B; B extends A C extends B; B extends A會起作用。 這確實使C instanceof BB instanceof A變為true ,但它不會根據需要復制原型屬性。 所以,我改寫了答案。]

讓我們來看看:

class A
  foo: 1
class B
  bar: 2
class C extends A
  baz: 3

此時, C::foo為1, C::baz為3.如果我們再運行

C extends B

B的實例( child.prototype = ... )覆蓋C的現有原型,因此只定義了C::bar

當我們使用class X extends Y語法時,這不會發生,因為屬性僅在其原型被覆蓋后附加到X的原型。 所以,讓我們寫一個包裝周圍extends ,節省了現有的原型屬性,然后恢復它們:

inherits = (child, parent) ->
  proto = child::
  child extends parent
  child::[x] = proto[x] for own x of proto when x not of child::
  child

將此應用於我們的示例:

inherits B, A
inherits C, B

console.log new C instanceof B, new B instanceof A  # true, true
console.log B::foo, B::bar, B::baz  # 1, 2, undefined
console.log C::foo, C::bar, C::baz  # 1, 2, 3

如果您想了解更多有關CoffeeScript類的內部工作原理的信息,您可能需要查看我的關於CoffeeScript的書 ,該書由PragProg的優秀人員發布。 :)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM