2017-04-25 26 views
1

私はドキュメントジェネレータを書いています。 DocumentItemインターフェイスがあります。これはドキュメントの一部です。インターフェイスのスライスに追加

type DocumentItem interface { 
    compose() string 
} 

たとえば、ドキュメントは段落と表で構成されます。

type Paragraph struct { 
    text string 
} 
type Table struct{} 

ParagraphTableタイプはDocumentItemインタフェースに対応します。

func (p *Paragraph) compose() string { 
    return "" 
} 

func (t *Table) compose() string { 
    return "" 
} 

Documentタイプはcontent []*DocumentItemフィールドが含まれています。

type Document struct { 
    content []*DocumentItem 
} 

私は、必要なデータ型を作成し、contentフィールドに追加しNewParagraph()NewTable()機能を可能にする方法を探しています。

func (d *Document) NewParagraph() *Paragraph { 
    p := Paragraph{} 
    d.content = append(d.content, &p) 
    return &p 
} 

func (d *Document) NewTable() *Table { 
    t := Table{} 
    d.content = append(d.content, &t) 
    return &t 
} 

対応する変数がドキュメントに含まれた後でデータを変更できるように、インタフェースポインタのスライスを使用します。

func (p *Paragraph) SetText(text string) { 
    p.text = text 
} 

func main() { 
    d := Document{} 
    p := d.NewParagraph() 
    p.SetText("lalala") 
    t := d.NewTable() 
    // ...  
} 

しかし、私は、コンパイラのエラーを取得:

cannot use &p (type *Paragraph) as type *DocumentItem in append 
cannot use &t (type *Table) as type *DocumentItem in append 

私はDocumentItemインターフェイスに種類をキャストした場合、私は1つのタイプの場合には他とは異なる場合があり、特定の機能へのアクセスを失うことになります。たとえば、段落にテキストを追加し、セルの行を追加して、表のセルにテキストを追加します。

それはまったく可能ですか?インタフェース値に包まれた動的な値がポインタである場合、あなたは何を失うことなく、

content []DocumentItem 

全例がhttps://play.golang.org/p/uJfKs5tJ98

答えて

4

で、インターフェースするためのインターフェイスのみのスライスをポインタを使用しないでください。指示されたオブジェクトを変更することができます。

これは変更する必要があった唯一のものでした。確認するために、私は最後に印刷を追加しました:

fmt.Printf("%+v", p) 

は出力(Go Playground上でそれを試してみてください):

&{text:lalala} 
関連する問題