r - Force which() to return only first match

时间:2015-06-25 18:51:20

标签: r

Part of a function I'm working on uses the following code to take a data frame and reorder its columns on the basis of the largest (absolute) value in each column. ord <- order(abs(apply(dfm,2,function(x) x[which(abs(x) == max(abs(x)), arr.ind = TRUE)]))) For the most part, this works fine, but with the dataset I'm working on, I occasionally get data that looks like this: a <- rnorm(10,5,7); b <- rnorm(10,0,1); c <- rep(1,10) dfm <- data.frame(A = a, B = b, C = c) > dfm A B C 1 0.6438373 -1.0487023 1 2 10.6882204 0.7665011 1 3 -16.9203506 -2.5047946 1 4 11.7160291 -0.1932127 1 5 13.0839793 0.2714989 1 6 11.4904625 0.5926858 1 7 -5.9559206 0.1195593 1 8 4.6305924 -0.2002087 1 9 -2.2235623 -0.2292297 1 10 8.4390810 1.1989515 1 When that happens, the above code returns a "non-numeric argument to mathematical function" error at the abs() step. (And if I get rid of the abs() step because I know, due to transformation, my data will be all positive, order() returns: "unimplemented type 'list' in 'orderVector1'".) This is because which() returns all the 1's in column C, which in turn makes apply() spit out a list, rather than a nice tidy vector. My question is this: How can I make which() JUST return one value for column C in this case? Alternately, is there a better way to write this code to do what I want it to (reorder the columns of a matrix based on the largest value in each column, whether or not that largest value is duplicated) that won't have this problem?

2 个答案:

答案 0 :(得分:2)

If you want to select just the first element of the result, you can subset it with [1]: ord <- order(abs(apply(dfm,2,function(x) x[which(abs(x) == max(abs(x)), arr.ind = TRUE)][1])))

答案 1 :(得分:2)

To order the columns by their maximum element (in absolute value), you can do dfm[order(apply(abs(dfm),2,max))] Your code, with @CarlosCinelli's correction, should work fine, though.