2015-02-24 202 views
1

問題

我需要,其通過對於不同的範圍(例如,我測量電流和儀表計算測量的不確定度的函數,如果它是在2毫安的不確定性的範圍是測量值的0.1 % + 3 dig)。如果該函數能夠獲取矢量並返回矢量而不是數字,則更好。替代嵌套ifelse()中的R語句

我寫了很多if的函數,但它返回警告the condition has length > 1 and only the first element will be used。經過一段時間的研究,我發現R中的if s被設計用於處理表達式,該表達式可以計算出單個布爾值,而ifelse可以處理向量。

但由於有大約10個鏈else if s同樣的事情與ifelse s會相當醜陋。

if S:

S.I = function(I) { 
    if(I<=(2*10^(-6))){ 
     0.1*I/100 + 3*10^(-9) 
    } else if(I<=(20*10^(-6))) { 
     ... 
    } 
    ... 
} 

ifelse小號

S.I = function(I) { 
    ifelse(I<=(2*10^(-6)),0.1*I/100 + 3*10^(-9),ifelse(I<=(2*10^(-6)),...,ifelse(...))) 
} 

問題

有沒有在這種情況下ifelse秒的方法嗎?

+1

你能提供一個可重複的例子嗎? – Khashaa 2015-02-24 15:48:40

+0

您不必在同一行上完成'ifelse'。 – James 2015-02-24 15:52:17

+0

儘管不能像當前編寫的那樣將向量投入到「SI」中,但如果更容易,可以繼續使用if-else範例,然後使用可將向量傳遞給的向量化(SI)' – rawr 2015-02-24 15:53:37

回答

3

R中這樣做的通常方法可能是cut;這裏是一個例子。

## some sample current values 
I <- c(1e-6, 2e-6, 1e-5, 2e-5, 1e-4, 2e-4, 1e-3, 2e-3) 
## define the endpoints for the different ranges 
breaks <- c(-Inf, 2*10^(-6:3)) 
## for each range, define the percent of the original 
## and the amount to add 
percent <- c(0.10, 0.11, 0.12, 0.13) 
dig <- c(3e-9, 3e-8, 3e-7, 3e-6) 
## get the range that each value falls in 
range <- cut(I, breaks, labels=FALSE) 
## and multiply by the right percent and add the right extra amount 
I*percent[range]/100 + dig[range] 
1

正如您所指出的那樣,您的函數僅適用於單個值,因爲if不作用於矢量。解決方案是將每個向量的值逐個發送到函數。

[R提供了一組apply功能來做到這些(這就像一個循環,但速度更快):如果你想在矢量代碼申請S.I幾次

result = sapply(I_vector, S.I) 

,它可以是值得使用包裝:

wrapper_S.I = function(I) { return(sapply(I_vector, S.I)) } 
result = wrapper_S.I(I_vector) 

注:您還可以Vectorize創建包裝:

wrapper_S.I = Vectorize(S.I) 

它創建一個包含額外控件的包裝。