poorman: Replicando as funções de junção e filtragem de dplyr com base R

cupom com desconto - o melhor site de cupom de desconto cupomcomdesconto.com.br


Na minha última postagem, discuti a execução de operações split-apply-combine no R data.framese como esta funcionalidade foi usada dentro poorman – uma base R réplica de dplyr. Neste post, eu gostaria de falar sobre replicar dplyrJuntam e filtram a funcionalidade de junção, novamente usando nada além de base.

Antes de tudo, vamos configurar alguns dados para usar em nossos exemplos. Aqui eu crio dois data.frames; um contendo alturas associadas a nomes e IDs; o segundo contendo pesos também associado a alguns nomes e IDs. Algumas dessas combinações de ID e nome são comuns a ambas as tabelas (por exemplo, c("id" = 5, "name" = "C")), mas outros códigos são exclusivos de uma tabela ou de outra (por exemplo, c("id" = 1, "name" = "A"))

Observe que algumas vezes uma lista de elementos (aqui nome e ID) às vezes é chamada de tupla.

table1 

Ao trabalhar com dados como esse, podemos querer unir essas duas tabelas para que possamos usar mais facilmente os dados de ambas. Dentro base, a função que usamos para juntar tabelas é chamada merge(). Veremos como podemos usar essa função para realizar junções internas, esquerda, direita e total.

Junção interna

Uma junção interna seleciona registros que possuem valores correspondentes em ambas as tabelas nas colunas pelas quais estamos ingressando, retornando todas as colunas. Para table1 e table2, estaremos juntando as tabelas por "id" e "name" pois essas são as colunas comuns entre as duas tabelas.

Observe que, dependendo da sua circunstância, talvez você não queira participar de todas as colunas comuns. Por exemplo, você pode ter duas tabelas que possuem colunas com o mesmo nome, mas na verdade contêm dados diferentes.

Quando realizamos a junção interna, esperamos uma data.frame contendo os registros c("id" = 5, "name" = "C") e c("id" = 7, "name" = "D") já que esses registros existem nas duas tabelas.

Leia Também  Moorwand lança serviço de aquisição para facilitar margens reduzidas para bancos e comerciantes

Para executar uma junção interna, usamos o merge() função sem parâmetros adicionais, fornecendo as duas tabelas para mesclar.

merge(x = table1, y = table2)
#   id name height weight
# 1  5    C      2      4
# 2  7    D      2      5

Ao realizar uma junção, normalmente especificamos em quais colunas gostaríamos de participar. merge() é útil, pois elabora as colunas comuns entre os conjuntos de dados com o seguinte comando.

by 

Se quiséssemos, poderíamos passar os nomes das colunas explicitamente.

merge(x = table1, y = table2, by = c("id", "name"))
#   id name height weight
# 1  5    C      2      4
# 2  7    D      2      5

Dentro poorman, podemos usar o inner_join() para executar esse tipo de junção.

table1 %>% inner_join(table2)
# Joining, by = c("id", "name")
#   id name height weight
# 1  5    C      2      4
# 2  7    D      2      5

Associação à esquerda

Uma junção esquerda incluirá todas as linhas de table1 independentemente de haver ou não um registro correspondente no table2. Para os registros que não coincidem, a junção esquerda deixará as células como NA valores. Dentro base, realizamos esse tipo de associação com o merge() função, especificando all.x = TRUE.

merge(x = table1, y = table2, all.x = TRUE)
#   id name height weight
# 1  1    A      1     NA
# 2  3    B      2     NA
# 3  5    C      2      4
# 4  7    D      2      5
# 5  9    E      2     NA

Dentro poorman, esse tipo de junção pode ser realizado com left_join().

table1 %>% left_join(table2)
# Joining, by = c("id", "name")
#   id name height weight
# 1  1    A      1     NA
# 2  3    B      2     NA
# 3  5    C      2      4
# 4  7    D      2      5
# 5  9    E      2     NA

Right Join

Uma junção direita é o oposto de uma junção esquerda. Aqui o merge() A função retorna todas as linhas de table2 e as linhas correspondentes de table1; novamente preenchendo todas as células em branco com NA. Desta vez, especificamos all.y = TRUE.

merge(x = table1, y = table2, all.y = TRUE)
#   id name height weight
# 1  2    A     NA      2
# 2  4    B     NA      3
# 3  5    C      2      4
# 4  7    D      2      5

Dentro poorman, esse tipo de união pode ser realizado com, você adivinhou, right_join().

cupom com desconto - o melhor site de cupom de desconto cupomcomdesconto.com.br
table1 %>% right_join(table2)
# Joining, by = c("id", "name")
#   id name height weight
# 1  2    A     NA      2
# 2  4    B     NA      3
# 3  5    C      2      4
# 4  7    D      2      5
Leia Também  baRcodeR agora na geração de PDF com código de barras rOpenSci + online

Junção completa

Uma junção completa juntará todas as linhas de duas tabelas. Como as uniões esquerda e direita, qualquer linha que não contenha uma correspondência conterá NA nas células que estão faltando. Aqui nós especificamos all = TRUE dentro merge() para representar uma junção completa.

merge(x = table1, y = table2, all = TRUE)
#   id name height weight
# 1  1    A      1     NA
# 2  2    A     NA      2
# 3  3    B      2     NA
# 4  4    B     NA      3
# 5  5    C      2      4
# 6  7    D      2      5
# 7  9    E      2     NA

Finalmente poorman fornece full_join() para fazer esse tipo de associação.

table1 %>% full_join(table2)
# Joining, by = c("id", "name")
#   id name height weight
# 1  1    A      1     NA
# 2  2    A     NA      2
# 3  3    B      2     NA
# 4  4    B     NA      3
# 5  5    C      2      4
# 6  7    D      2      5
# 7  9    E      2     NA

Para junções de filtro, examinaremos alguns dados ligeiramente diferentes.

table1 

Semi-Join

Uma semi-junção é um pouco diferente dos outros tipos de junções que vimos até agora. Descrevemos uma semi-junção como uma “junção de filtro”, uma vez que uma semi-junção retorna as linhas em table1 onde as colunas da junção se formam table1 também são encontrados em table2. Portanto, ainda especificamos os nomes das colunas nas quais desejamos “ingressar” (neste exemplo, é c("pupil", "test")), razão pela qual isso é considerado uma associação, mas na verdade estamos realizando uma espécie de filtro em table1.

by 

Como estamos procurando as linhas em table1 que também estão em table2, estaremos usando [.data.frame para filtrar table1 pelas linhas correspondentes. Para fazer isso, tiraremos proveito de base::interaction().

interaction(table1[, by])
# [1] 1.A 1.B 2.A 2.B 3.A 3.B
# Levels: 1.A 2.A 3.A 1.B 2.B 3.B

Como você pode ver, o que essa função faz é calcular um vetor de níveis de fator que representa a interação das colunas especificadas. Então, o número antes do . é o aluno e a carta após o . é o teste que eles fizeram. Se fizermos isso para as duas tabelas, podemos descobrir quais níveis são %in% ambas as mesas. Como podemos ver abaixo, os resultados de %in% retorna um vetor lógico que podemos usar para filtrar table1.

interaction(table2[, by])
# [1] 1.A 2.A 2.B
# Levels: 1.A 2.A 1.B 2.B
rows 

Então aqui podemos ver que níveis 1.A, 2.A e 2.B aparecer em ambos table1 e table2. Então agora podemos executar nosso filtro.

table1[rows, ]
#   pupil test score
# 1     1    A    60
# 3     2    A    65
# 4     2    B    80

A funcionalidade de semi-junção é fornecida por poorman usando o semi_join() função.

table1 %>% semi_join(table2)
# Joining, by = c("pupil", "test", "score")
#   pupil test score
# 1     1    A    60
# 2     2    A    65
# 3     2    B    80

Anti-Join

Uma anti-junção é um pouco diferente de uma semi-junção, pois retorna todas as linhas de table1 naquela não apareça em table2 ao “ingressar” nas colunas de junção. Usando nosso definido anteriormente rows variável, podemos tomar o inverso desse vetor lógico usando !.

rows 

poorman fornece uma cópia da funcionalidade anti-junção usando anti_join().

table1 %>% anti_join(table2)
# Joining, by = c("pupil", "test", "score")
#   pupil test score
# 1     1    B    70
# 2     3    A    85
# 3     3    B    70



cupom com desconto - o melhor site de cupom de desconto cupomcomdesconto.com.br