R Language
Podzbiór
Szukaj…
Wprowadzenie
Biorąc pod uwagę obiekt R, możemy wymagać osobnej analizy dla jednej lub więcej części zawartych w nim danych. Proces uzyskiwania tych części danych z danego obiektu nazywa się subsetting
.
Uwagi
Brakujące wartości:
Brakujące wartości ( NA
) użyte w podzbiorze z [
zwracają NA
od indeksu NA
wybiera nieznany element, a zatem zwraca NA w odpowiednim elemencie.
„Domyślnym” typem NA
jest „logiczny” ( typeof(NA)
), co oznacza, że jak każdy „logiczny” wektor użyty w podzestawie zostanie przetworzony, aby dopasować długość podzestawu obiektu. Zatem x[NA]
jest równoważne x[as.logical(NA)]
który jest równoważny x[rep_len(as.logical(NA), length(x))]
a zatem zwraca brakującą wartość ( NA
) dla każdego elementu x
. Jako przykład:
x <- 1:3
x[NA]
## [1] NA NA NA
Podczas indeksowania za pomocą „numerycznej” / „liczby całkowitej” NA
wybiera pojedynczy element NA
(dla każdej NA
w indeksie):
x[as.integer(NA)]
## [1] NA
x[c(NA, 1, NA, NA)]
## [1] NA 1 NA NA
Podzbiór poza granicami:
Operator [
z jednym argumentem dopuszcza indeksy o > length(x)
i zwraca NA
dla wektorów atomowych lub NULL
dla wektorów ogólnych. W przeciwieństwie do tego, gdy [[
i gdy [
zostanie przekazane więcej argumentów (tj. Podzbiór poza obrębem obiektów o length(dim(x)) > 2
), zwracany jest błąd:
(1:3)[10]
## [1] NA
(1:3)[[10]]
## Error in (1:3)[[10]] : subscript out of bounds
as.matrix(1:3)[10]
## [1] NA
as.matrix(1:3)[, 10]
## Error in as.matrix(1:3)[, 10] : subscript out of bounds
list(1, 2, 3)[10]
## [[1]]
## NULL
list(1, 2, 3)[[10]]
## Error in list(1, 2, 3)[[10]] : subscript out of bounds
Zachowanie jest takie samo w przypadku podzbioru z wektorami „znakowymi”, które również nie są dopasowane do atrybutu „nazwy” obiektu:
c(a = 1, b = 2)["c"]
## <NA>
## NA
list(a = 1, b = 2)["c"]
## <NA>
## NULL
Tematy pomocy:
Zobacz ?Extract
aby uzyskać dodatkowe informacje.
Wektory atomowe
Wektory atomowe (z wyłączeniem list i wyrażeń, które są również wektorami) są podzbiór za pomocą operatora [
# create an example vector
v1 <- c("a", "b", "c", "d")
# select the third element
v1[3]
## [1] "c"
[
Operator może również przyjąć wektor jako argument. Na przykład, aby wybrać pierwszy i trzeci element:
v1 <- c("a", "b", "c", "d")
v1[c(1, 3)]
## [1] "a" "c"
Czasami możemy wymagać pominięcia określonej wartości w wektorze. Można to osiągnąć za pomocą znaku ujemnego ( -
) przed indeksem tej wartości. Na przykład, aby pominąć, aby pominąć pierwszą wartość z v1, użyj v1[-1]
. Można to w prosty sposób rozszerzyć na więcej niż jedną wartość. Na przykład v1[-c(1,3)]
.
> v1[-1]
[1] "b" "c" "d"
> v1[-c(1,3)]
[1] "b" "d"
W niektórych przypadkach chcielibyśmy wiedzieć, zwłaszcza gdy długość wektora jest duża, indeks określonej wartości, jeśli istnieje:
> v1=="c"
[1] FALSE FALSE TRUE FALSE
> which(v1=="c")
[1] 3
Jeśli wektor atomowy ma nazwy (atrybut names
), można go podzielić na wektor znaków:
v <- 1:3
names(v) <- c("one", "two", "three")
v
## one two three
## 1 2 3
v["two"]
## two
## 2
Za pomocą operatora [[
można również indeksować wektory atomowe, z tą różnicą, że akceptuje wektor indeksujący o długości jednego i usuwa wszelkie obecne nazwy:
v[[c(1, 2)]]
## Error in v[[c(1, 2)]] :
## attempt to select more than one element in vectorIndex
v[["two"]]
## [1] 2
Wektory można również podzielić na części za pomocą wektora logicznego. W przeciwieństwie do podzbioru z wektorami numerycznymi i znakowymi, wektor logiczny zastosowany do podzbioru musi być równy długości wektora, którego elementy są wyodrębniane, więc jeśli wektor logiczny y
jest użyty do podzbioru x
, tj. x[y]
, jeśli length(y) < length(x)
następnie y
zostanie przetworzone, aby dopasować length(x)
:
v[c(TRUE, FALSE, TRUE)]
## one three
## 1 3
v[c(FALSE, TRUE)] # recycled to 'c(FALSE, TRUE, FALSE)'
## two
## 2
v[TRUE] # recycled to 'c(TRUE, TRUE, TRUE)'
## one two three
## 1 2 3
v[FALSE] # handy to discard elements but save the vector's type and basic structure
## named integer(0)
Listy
Listę można podzielić na [
:
l1 <- list(c(1, 2, 3), 'two' = c("a", "b", "c"), list(10, 20))
l1
## [[1]]
## [1] 1 2 3
##
## $two
## [1] "a" "b" "c"
##
## [[3]]
## [[3]][[1]]
## [1] 10
##
## [[3]][[2]]
## [1] 20
l1[1]
## [[1]]
## [1] 1 2 3
l1['two']
## $two
## [1] "a" "b" "c"
l1[[2]]
## [1] "a" "b" "c"
l1[['two']]
## [1] "a" "b" "c"
Zauważ, że wynik l1[2]
wciąż jest listą, ponieważ [
operator wybiera elementy listy, zwracając mniejszą listę. [[
Operator wyodrębnia elementy listy, zwracając obiekt typu elementu listy.
Elementy można indeksować według numeru lub ciągu znaków nazwy (jeśli istnieje). Wiele elementów można wybrać za pomocą [
przekazując wektor liczb lub ciągów nazw. Indeksowanie wektorem o length > 1
w [
i [[
zwraca „lista” z wymienionych elementów i rekurencyjne podgrupie (jeśli są dostępne), odpowiednio:
l1[c(3, 1)]
## [[1]]
## [[1]][[1]]
## [1] 10
##
## [[1]][[2]]
## [1] 20
##
##
## [[2]]
## [1] 1 2 3
W porównaniu do:
l1[[c(3, 1)]]
## [1] 10
co jest równoważne z:
l1[[3]][[1]]
## [1] 10
Operator $
pozwala wybierać elementy listy wyłącznie według nazwy, ale w przeciwieństwie do [
i [[
, nie wymaga cudzysłowów. Jako operator infix $
może przyjąć tylko jedną nazwę:
l1$two
## [1] "a" "b" "c"
Ponadto operator $
domyślnie dopuszcza częściowe dopasowanie:
l1$t
## [1] "a" "b" "c"
w przeciwieństwie do [[
gdzie należy określić, czy dozwolone jest częściowe dopasowanie:
l1[["t"]]
## NULL
l1[["t", exact = FALSE]]
## [1] "a" "b" "c"
Ustawiając options(warnPartialMatchDollar = TRUE)
, pojawia się „ostrzeżenie”, gdy następuje częściowe dopasowanie z $
:
l1$t
## [1] "a" "b" "c"
## Warning message:
## In l1$t : partial match of 't' to 'two'
Matryce
Dla każdego wymiaru obiektu operator [
przyjmuje jeden argument. Wektory mają jeden wymiar i biorą jeden argument. Macierze i ramki danych mają dwa wymiary i przyjmują dwa argumenty, podane jako [i, j]
gdzie i
to wiersz, a j
to kolumna. Indeksowanie zaczyna się od 1.
## a sample matrix
mat <- matrix(1:6, nrow = 2, dimnames = list(c("row1", "row2"), c("col1", "col2", "col3")))
mat
# col1 col2 col3
# row1 1 3 5
# row2 2 4 6
mat[i,j]
jest elementem i
-tego rzędu j
-ty kolumna macierzy mat
. Na przykład wartość i
2
oraz wartość j
1
daje liczbę w drugim wierszu i pierwszej kolumnie macierzy. Pominięcie i
lub j
zwraca wszystkie wartości w tym wymiarze.
mat[ , 3]
## row1 row2
## 5 6
mat[1, ]
# col1 col2 col3
# 1 3 5
Gdy macierz ma nazwy wierszy lub kolumn (nie jest wymagane), można ich użyć do podzbioru:
mat[ , 'col1']
# row1 row2
# 1 2
Domyślnie wynik podzbioru zostanie uproszczony, jeśli to możliwe. Jeśli podzbiór ma tylko jeden wymiar, jak w powyższych przykładach, wynikiem będzie wektor jednowymiarowy, a nie macierz dwuwymiarowa. To ustawienie domyślne można zastąpić argumentem drop = FALSE
dla [
:
## This selects the first row as a vector
class(mat[1, ])
# [1] "integer"
## Whereas this selects the first row as a 1x3 matrix:
class(mat[1, , drop = F])
# [1] "matrix"
Oczywiście wymiarów nie można usunąć, jeśli sam wybór ma dwa wymiary:
mat[1:2, 2:3] ## A 2x2 matrix
# col2 col3
# row1 3 5
# row2 4 6
Wybieranie poszczególnych wpisów macierzy według ich pozycji
Możliwe jest również użycie macierzy Nx2 do wybrania N pojedynczych elementów z macierzy (np. Jak działa układ współrzędnych). Jeśli chcesz wyodrębnić w wektorze wpisy macierzy w (1st row, 1st column), (1st row, 3rd column), (2nd row, 3rd column), (2nd row, 1st column)
można to łatwo zrobić, tworząc macierz indeksów o tych współrzędnych i wykorzystując ją do podzestawu macierzy:
mat
# col1 col2 col3
# row1 1 3 5
# row2 2 4 6
ind = rbind(c(1, 1), c(1, 3), c(2, 3), c(2, 1))
ind
# [,1] [,2]
# [1,] 1 1
# [2,] 1 3
# [3,] 2 3
# [4,] 2 1
mat[ind]
# [1] 1 5 6 2
W powyższym przykładzie pierwsza kolumna ind
odnosi się do wierszy w mat
, druga kolumna ind
odnosi się do kolumn w mat
.
Ramki danych
Podzbiór ramki danych na mniejszą ramkę danych można osiągnąć tak samo, jak podzestaw listy.
> df3 <- data.frame(x = 1:3, y = c("a", "b", "c"), stringsAsFactors = FALSE)
> df3
## x y
## 1 1 a
## 2 2 b
## 3 3 c
> df3[1] # Subset a variable by number
## x
## 1 1
## 2 2
## 3 3
> df3["x"] # Subset a variable by name
## x
## 1 1
## 2 2
## 3 3
> is.data.frame(df3[1])
## TRUE
> is.list(df3[1])
## TRUE
Podzbiór ramki danych na wektor kolumny można wykonać za pomocą podwójnych nawiasów kwadratowych [[]] lub operatora znaku dolara $.
> df3[[2]] # Subset a variable by number using [[ ]]
## [1] "a" "b" "c"
> df3[["y"]] # Subset a variable by name using [[ ]]
## [1] "a" "b" "c"
> df3$x # Subset a variable by name using $
## [1] 1 2 3
> typeof(df3$x)
## "integer"
> is.vector(df3$x)
## TRUE
Podzbioru do danych w postaci dwuwymiarowej matrycy może być realizowane za pomocą i
i j
warunki.
> df3[1, 2] # Subset row and column by number
## [1] "a"
> df3[1, "y"] # Subset row by number and column by name
## [1] "a"
> df3[2, ] # Subset entire row by number
## x y
## 2 2 b
> df3[ , 1] # Subset all first variables
## [1] 1 2 3
> df3[ , 1, drop = FALSE]
## x
## 1 1
## 2 2
## 3 3
Uwaga: Podzbiór tylko przez j
(kolumna) upraszcza własny typ zmiennej, ale podzbiór przez samo i
zwraca data.frame
, ponieważ różne zmienne mogą mieć różne typy i klasy. Ustawienie parametru drop
na FALSE
powoduje zachowanie ramki danych.
> is.vector(df3[, 2])
## TRUE
> is.data.frame(df3[2, ])
## TRUE
> is.data.frame(df3[, 2, drop = FALSE])
## TRUE
Inne przedmioty
Operatory [
i [[
są prymitywnymi funkcjami, które są ogólne. Oznacza to, że każdy obiekt w R (w szczególności isTRUE(is.object(x))
--ie ma wyraźny atrybut „klasy”) może mieć swoje określone zachowanie, gdy jest podzbiór; tj. ma własne metody dla [
i / lub [[
.
Tak jest na przykład w przypadku obiektów „data.frame” ( is.object(iris)
), w których zdefiniowane są metody [.data.frame
i [[.data.frame
, które mają wyświetlać zarówno „matrycę” i podzbiór podobny do „listy”. Wymuszając błąd przy podzestawie „data.frame”, widzimy, że w rzeczywistości funkcja [.data.frame
została wywołana, gdy -just- użyliśmy [
.
iris[invalidArgument, ]
## Error in `[.data.frame`(iris, invalidArgument, ) :
## object 'invalidArgument' not found
Bez dalszych szczegółów na temat bieżącego tematu, przykład [
metoda:
x = structure(1:5, class = "myClass")
x[c(3, 2, 4)]
## [1] 3 2 4
'[.myClass' = function(x, i) cat(sprintf("We'd expect '%s[%s]' to be returned but this a custom `[` method and should have a `?[.myClass` help page for its behaviour\n", deparse(substitute(x)), deparse(substitute(i))))
x[c(3, 2, 4)]
## We'd expect 'x[c(3, 2, 4)]' to be returned but this a custom `[` method and should have a `?[.myClass` help page for its behaviour
## NULL
Możemy przezwyciężyć wysyłanie metody [
za pomocą równoważnego .subset
(i .subset2
dla [[
). Jest to szczególnie przydatne i wydajne podczas programowania własnych „klas” i pozwala uniknąć obejścia (np. unclass(x)
) podczas wydajnego obliczania naszych „klas” (unikanie wysyłania metod i kopiowania obiektów):
.subset(x, c(3, 2, 4))
## [1] 3 2 4
Indeksowanie wektorowe
W tym przykładzie użyjemy wektora:
> x <- 11:20
> x
[1] 11 12 13 14 15 16 17 18 19 20
Wektory R są indeksowane 1, więc na przykład x[1]
zwróci 11
. Możemy również wyodrębnić podwektor wektora x
, przekazując wektor indeksów operatorowi nawiasu:
> x[c(2,4,6)]
[1] 12 14 16
Jeśli miniemy wektor indeksów ujemnych, R zwróci sub-wektor z wykluczonymi określonymi indeksami:
> x[c(-1,-3)]
[1] 12 14 15 16 17 18 19 20
Możemy również przekazać wektor boolowski operatorowi nawiasu, w którym to przypadku zwraca sub-wektor odpowiadający współrzędnym, dla których wektor indeksowania ma wartość TRUE
:
> x[c(rep(TRUE,5),rep(FALSE,5))]
[1] 11 12 13 14 15 16
Jeśli wektor indeksowania jest krótszy niż długość tablicy, zostanie powtórzony, jak w:
> x[c(TRUE,FALSE)]
[1] 11 13 15 17 19
> x[c(TRUE,FALSE,FALSE)]
[1] 11 14 17 20
Elementwise Matrix Operations
Niech A i B będą dwiema matrycami tego samego wymiaru. Operatory +
, -
, /
, *
, ^
gdy są używane z macierzami o tym samym wymiarze, wykonują wymagane operacje na odpowiednich elementach macierzy i zwracają nową macierz o tym samym wymiarze. Operacje te są zwykle nazywane operacjami elementarnymi.
Operator | A op B. | Znaczenie |
---|---|---|
+ | A + B | Dodanie odpowiednich elementów A i B |
- | A - B | Odejmuje elementy B od odpowiednich elementów A |
/ | A / B | Dzieli elementy A przez odpowiadające im elementy B |
* | A * B | Mnoży elementy A przez odpowiednie elementy B |
^ | A ^ (- 1) | Na przykład daje macierz, której elementy są odwrotnością A |
Aby uzyskać „prawdziwe” mnożenie macierzy, jak widać w Algebrze liniowej , użyj %*%
. Na przykład, pomnożenie A przez B wynosi: A %*% B
Wymagania wymiarowe są takie, że ncol()
z A
jest takie samo jak nrow()
z B
Niektóre funkcje używane z macierzami
Funkcjonować | Przykład | Cel, powód |
---|---|---|
nrow () | nrow (A) | określa liczbę rzędów A |
ncol () | ncol (A) | określa liczbę kolumn A |
rownames () | rownames (A) | wypisuje nazwy wierszy macierzy A |
colnames () | nazwy kolorów (A) | wypisuje nazwy kolumn macierzy A |
rowMeans () | rowMeans (A) | oblicza średnie z każdego rzędu macierzy A |
colMeans () | colMeans (A) | oblicza średnie z każdej kolumny macierzy A |
upper.tri () | upper.tri (A) | zwraca wektor, którego elementy są górne |
macierz trójkątna macierzy kwadratowej A | ||
lower.tri () | lower.tri (A) | zwraca wektor, którego elementy są niższe |
macierz trójkątna macierzy kwadratowej A | ||
det () | det (A) | daje wyznacznik macierzy A |
rozwiązać() | rozwiązać (A) | skutkuje odwrotnością macierzy niepodzielnej A |
diag () | diag (A) | zwraca macierz ukośną, której elementy zdiagnozowane to zero i |
przekątne są takie same jak w macierzy kwadratowej A | ||
t () | t (A) | zwraca transpozycję macierzy A |
eigen () | własny (A) | ponownie oblicza wartości własne i wektory własne macierzy A |
is.matrix () | is.matrix (A) | zwraca PRAWDA lub FAŁSZ w zależności od tego, czy A jest macierzą, czy nie. |
as.matrix () | as.matrix (x) | tworzy macierz z wektora x |