2011-11-05 64 views
0

就編程的最佳/最常見實踐而言,代碼應該在哪裏防止某些函數被調用,同時記住性能?何時阻止函數調用?

例如,如果我有一個函數可以在錯誤的時間被調用時中斷,那麼這些方法中哪個最常見?

答:

Data *someData = new Data; 

while(running) 
{ 
    ProcessData(someData); 
}; 

void ProcessData(Data *data) 
{ 
    if(data) 
     data->member = 5; 
} 

B:

Data *someData = new Data; 

while(running) 
{ 
    if(someData) 
     ProcessData(someData); 
}; 

void ProcessData(Data *data) 
{ 
    data->member = 5; 
} 

編輯:澄清一下,我問功能是否自己應該做的驗證或依賴客戶端代碼不調用的函數,而處於錯誤的狀態。

在函數深度調用5次的情況下,爲每個函數添加驗證可能會給代碼添加相當多的批量,並可能會損害性能,但更重要的是降低代碼的可讀性。

所以我問什麼普通開發者會期望在這種情況下

+0

你是問,如果過程數據()應承擔「數據」是有效的,它被稱爲前,還是應該過程數據()默默若無效忽略? – seand

+1

也許斷言可能會有幫助,如果不好的輸入是不正確的編碼的結果。他們將從發佈代碼中刪除。 –

回答

1

驗證方法需要有效的參數有性能上的成本,也有一個「成本」時發生錯誤。例如,內核函數不能讓內部崩潰 - 這會導致整個系統崩潰。

一般來說,我所做的是看看呼叫者和被呼叫者的耦合程度如何。如果它們都在你的直接控制之下,那麼被調用者可能會相信它不會被廢話調用。但是,如果你有更少的控制,那麼它可能需要更多的驗證。

3

你的意思是什麼時候做輸入驗證?那麼,如果可以在O(1)時間檢查並且n可能非常大,那麼在您外部> = O(n)循環中。

但是,如果選擇,因爲在你的例子,在其客戶端代碼一次公開標榜函數內部或做一次檢查,通過各種手段做到這一點的函數之間。否則,這將是一個過早優化的例子,它是所有惡魔之根(TM)。

+0

當然,每個調用函數的人都需要知道它不能在某些對象上運行。如果你在函數內部檢查,你會將這個實現細節隱藏到外部世界。 – hochl

3

該特定情況下,最常用的方法可能是

void ProcessData(Data& data) { 
    data.member = 5; 
} 

或者

void Data::Process() { 
    member = 5; 
} 

那些都可以在沒有一個有效的Data對象在行動被稱爲的,所以沒有必要進行無關測試。另外,文檔是你的朋友:如果一個函數只能在初始化主事件循環後調用,那麼確保函數的文檔說「初始化主事件循環後只調用這個函數」。

不止這取決於你的具體情況。

1

嘛,總的來說,它還挺更好一點,如果你決定是否要調用一個函數長鏈高達儘可能以避免不必要的調用/返回。這麼說,我真的不明白你的問題或例子好...