2016-11-06 67 views
2

我是面向對象編程的新手,我認爲這對於經驗豐富的面向對象程序員來說應該是一個簡單的概念,但我肯定會爲此而苦苦掙扎。如何將值從一個類的方法傳遞給Typescript中的另一個類的方法?

在我Angular2應用程序我有一個HTTPService類,如下圖所示:

http.service.ts

@Injectable() 
export class HttpService { 
    constructor(private http: Http) { } 
    addLeaf(parentId, label, name){ 
     var headers = new Headers(); 
     headers.append('Content-Type', 'application/json'); 
     return this.http.post('http://localhost:8000/addleaf/', 
     {'parentId':parentId,'label':label, 'name':name}, 
     { headers: headers }) 
     .map(res => res).subscribe();   
} 

我嘗試從如下另一個類中調用此方法:

leaf.ts

import { HttpService } from './http.service'; 

export class Leaf{ 
name: string; 
... 
http: Http; // very unsure about these two lines 
private httpService: HttpService = new HttpService(this.http) 
constructor(input){ 
    this.name = input.name; 
... 
add(){ 
    //what should go here? 
    this.httpservice.addLeaf(this.id, this.label, this.name); 
    //error -> cannot read property 'post' of undefined 
} 

閱讀this,我試着創建一個HttpService類的實例,但是我得到了post函數不存在的錯誤。也沒有運氣把httpService放在構造函數中。

我調用該方法在我的HTML這樣的:

(click)="leaf.add()" 

編輯:以下@ peeskillet的回答我修改leaf.ts並添加leaf.component.ts如圖所示:

葉.TS

export class Leaf{ 
    name: string; 
    ... 
    constructor(input){ 
     this.name = input.name; 
     ... 
    add(){ 
     //what should go here? 
    } 
} 

leaf.component.ts

@Component({ 
    providers: [HttpService], 
}) 

export class LeafComponent { 
    leaf: Leaf; 
    constructor(private httpService: HttpService) { 
     this.httpService.addLeaf(this.leaf.id, this.leaf.type, this.leaf.name) 
    } 
} 

服務工作正常,如果我在的地方則params的寫預定義的字符串,但還是不知道我怎麼能通過點擊的葉子的參數了這一點。

回答

1

使用Angular,我們使用dependency injectionInversion of Control。這意味着我們不會自己創建服務,而是讓Angular創建它。那麼我們只需詢問的服務,然後Angular將解決服務所具有的任何依賴關係。舉個例子

@Injectable() 
class Service { 
    constructor(private http: Http) {} 
} 

這裏,ServiceHttp依賴。 Http不是我們可以憑空攫取的東西。我們不能只做

let service = new Service(new Http()); 

Http也依賴於一些其他服務。這裏是什麼它的構造看起來像

class Http { 
    constructor(backend: ConnectionBackend, options: RequestOptions) {} 
} 

你可能會認爲,也許你可以只用ConnectionBackendRequestOptions

new Http(new ConnectionBackend(), new RequestOptions())` 

實例,但你不能做到這一點無論是作爲ConnectionBackend也需要依賴。正因爲如此,我們使用控制反轉。我們只是將服務添加到容器中,當請求服務時,Angular查找服務,請參閱Http,並看到Http需要ConnectionBackendRequestOptions等,並且Angular將創建所有項目在其所有這些項目的註冊表中,並將它們放在一起,如Voltron。然後它會給我們提供服務,人口衆多。

因此增加我們的服務容器,我們首先需要添加對服務的Injectable裝飾

@Injectable() 
class Service { 
    constructor(private http: Http) {} 
} 

然後,我們需要把它添加到@NgModule.providers

@NgModule({ 
    imports: [ HttpModule ], 
    providers: [ Service ] 
}) 
class AppModule {} 

現在,每當我們請求Service,它將完全填充Http(位於HttpModule)。

我們如何要求的服務是通過任何其他服務或組件(指令,管等)

@Component({ 
}) 
class MyComponent { 
    constructor(private service: Service) {} 
} 

的構造函數通過觀察Service類型爲構造函數的參數,角知道來查找Service在它的容器中,然後傳遞給我們。這是依賴注入和控制反轉的基礎。

在你的情況下Leaf。如果意味着是一種服務,那麼你可以做同樣的

@Injectable() 
class Leaf { 
    constructor(private service: Service) {} 
} 

@NgModule({ 
    imports: [ HttpModule ], 
    providers: [ Leaf, Service ] 
}) 
class AppModule {} 

如果你不希望添加Leaf的供應商,你不需要。只是做

@Component({}) 
class MyComponent { 
    leaf: Leaf; 

    constructor(private service: Service) { 
    this.leaf = new Leaf(service); 
    } 
} 
+0

感謝您對服務的解釋,但我仍然不清楚如何將參數傳遞給該服務的方法。葉在我的情況下是一個對象,有幾個屬性(名稱,標籤等),我想將這些值傳遞給我的http服務。 – Arash

+1

我不認爲該服務應該是葉的成員。我認爲你應該只有組件的葉和服務成員。然後,當您想發送請求時,只需從葉中獲取屬性並將其傳遞給服務方法即可。 –

+0

是的,我從葉中刪除了服務並創建了一個新組件,在那裏添加了該服務,如果我在參數的位置放置了預定義的字符串,該服務可以正常工作,但我仍然不知道如何掛接我的當我點擊一個葉子對象到該服務時的參數。我將編輯該問題進行詳細說明。 – Arash

相關問題