まずサンプルデータを作ります。

irisに条件を示す2つの列を加えます。 str.a列とstr.b列の値によって、新規の列str.cにどの列のデータをコピーしてくるかが変わります。

x <- cbind(iris, data.frame(str.a=iris$Sepal.Length>median(iris$Sepal.Length), str.b=iris$Species=="virginica"))

では、抽出処理を実行します。まずは基本的なforループの場合。

# str.aがTRUEであるときはSepal.Lengthからのデータ、str.aがFALSEでstr.bがTRUEの時はPetal.Lengthからのデータ、それ以外の時はSepal.Widthからのデータを採用する
str.c <- NULL
system.time(for(i in 1:nrow(x)) { if(x[i,"str.a"]) col<-"Sepal.Length" else if(x[i, "str.b"]) col<-"Petal.Length" else col <- "Sepal.Width" ; str.c <- append(str.c, x[i,col]) })
##    user  system elapsed 
##   0.004   0.000   0.004
str(str.c)
##  num [1:150] 3.5 3 3.2 3.1 3.6 3.9 3.4 3.4 2.9 3.1 ...

これだと、ループ中で条件判断が多数入って効率が悪いので、ループに入る前に条件判断をしてしまいましょう。idxは1から3までの値をとり、cols[idx]は、idxが1ならSepal.Length, 2ならPetal.Length, 3ならSepal.Lengthとなります。

cols <- c("Sepal.Length","Petal.Length", "Sepal.Width")
idx <- rep(3, nrow(x))
idx[x$str.a] <- 1
idx[!x$str.a & x$str.b] <- 2

では、先ほどのループの中身をこのcols[idx]を使って書き換えてみましょう。

str.c <- NULL
system.time(for(i in 1:nrow(x)) { str.c <- append(str.c,x[i,cols[idx[i]]])})
##    user  system elapsed 
##   0.003   0.000   0.003
str(str.c)
##  num [1:150] 3.5 3 3.2 3.1 3.6 3.9 3.4 3.4 2.9 3.1 ...

若干高速化されているのがわかります。 次に、Rらしいという点ではapply系列関数を使ってみても良いかと思います。

system.time(str.c <- sapply(1:nrow(x), function(i){x[i,cols[idx[i]]]}))
##    user  system elapsed 
##   0.002   0.000   0.002
str(str.c)
##  num [1:150] 3.5 3 3.2 3.1 3.6 3.9 3.4 3.4 2.9 3.1 ...

今回ももしかしたら高速化されているのかも?という結果になりましたが、apply系もforループも実行速度の違いはそれほど大きくないようです。