2015-07-06 14 views
9

Ich habe eine Liste (in R), wo die Elemente verschiedene Datentypen sind, z. B. das erste Element ist numerisch und das zweite Element ist ein Zeichen. Ich möchte auf jedes Element eine andere Funktion anwenden. Im folgenden Beispiel versuche ich beispielsweise, die Summenfunktion nur auf das erste Element und die Längenfunktion nur auf das zweite Element anzuwenden. Gibt es eine Möglichkeit, auf jedes Element einer Liste eine andere Funktion anzuwenden (ohne die Liste zu trennen)?R verschiedene Funktionen für jedes Element der Liste

data <- list(
    A = rnorm(10), 
    B = letters[1:10] 
) 

lapply(data, list(sum, length)) 

mapply(function(x) sum, length, data) 

Antwort

16

Wie wäre es

mapply(function(a,b) b(a), data, list(sum, length)) 

Beachten Sie, dass wir auch die Funktionen in mapply in eine Liste setzen.

+0

konnte Sie machen Sie etwas Ähnliches mit 'do.call', aber Sie müssen' data' leicht anpassen, um eine Liste von Listen zu sein. – joran

+0

... Interessanterweise scheint es (das Ignorieren der Notwendigkeit, jedes Argument zu recyceln), einfach eine 'for' -Schleife zu schreiben, die jede Funktion nacheinander anwendet, ~ 5x schneller. – joran

+0

Gut geschriebene For-Loops sind nach meiner Erfahrung normalerweise schneller, obwohl die Geschwindigkeit normalerweise nicht so groß ist. – MrFlick

6

Ich würde so etwas wie

sapply(data, function(x) (if(is.character(x)) length else sum)(x)) 

Komplizierte Alternativen tun. Wenn die Geschwindigkeit wichtig ist, sollte vapply schneller sein:

vapply(data, function(x) (if(is.character(x)) length else sum)(x), numeric(1)) 

Wenn Sie length oft verwenden müssen, es schnell ist lengths zu verwenden (erhältlich in R 3.2.0+):

res   <- lengths(data) 
get_sum  <- !sapply(data,is.character) 
res[get_sum] <- sapply(data[get_sum],sum) 
Verwandte Themen