Como obter o VLOOKUP para retornar a correspondência * last *?

10

Estou acostumado a trabalhar com o VLOOKUP, mas desta vez tenho um desafio. Eu não quero o primeiro valor correspondente, mas o último. Como? (Estou trabalhando com o LibreOffice Calc, mas uma solução do MS Excel deve ser igualmente útil.)

A razão é que eu tenho duas colunas de texto com milhares de linhas, digamos que uma é uma lista de beneficiários da transação (Amazon, Ebay, empregador, mercearia, etc.) e a outra é uma lista de categorias de gastos (salários , impostos, casa, aluguel, etc.). Algumas transações não têm a mesma categoria de gastos, e eu quero pegar a mais usada recentemente. Observe que a lista é classificada por nenhuma das colunas (na verdade, por data) e não quero alterar a ordem de classificação.

O que eu tenho (excluindo a manipulação de erros) é a fórmula usual de "primeira correspondência":

=VLOOKUP( 
[payee field] , [payee+category range] , [index of category column] , 
0 )

Eu já vi soluções assim, mas Eu recebo #DIV/0! errors:

=LOOKUP(2 , 1/( [payee range] = [search value] ) , [category range] )

A solução pode ser qualquer fórmula, não necessariamente VLOOKUP. Também posso trocar as colunas de beneficiário / categoria. Apenas nenhuma alteração na coluna de classificação, por favor.

Pontos de bônus para uma solução que escolha o valor mais frequente em vez do último!

    
por Torben Gundtofte-Bruun 11.07.2014 / 20:46

6 respostas

3

Você pode usar uma fórmula de matriz para obter dados do último registro correspondente.

=INDEX(IF($A$1:$A$20="c",$B$1:$B$20),MAX(IF($A$1:$A$20="c",ROW($A$1:$A$20))))

Insira a fórmula usando Ctrl + Deslocar + Enter .

Isso funciona como a construção INDEX / MATCH de um VLOOKUP , mas com um MAX condicional usado em vez de MATCH .

Observe que isso pressupõe que sua tabela começa na linha 1. Se seus dados começarem em uma linha diferente, você precisará ajustar a parte ROW(...) subtraindo a diferença entre a linha superior e 1.

    
por 11.07.2014 / 21:18
2

(respondendo aqui como nenhuma questão separada para dados classificados.)

Se os dados foram classificados, você pode usar VLOOKUP com range_lookup argumento TRUE (ou omitido, já que é o padrão), que é oficialmente descrito para o Excel como "pesquisa para correspondência aproximada ".

Em outras palavras, para dados classificados:

  • definir o último argumento como FALSE retorna o valor primeiro e
  • definir o último argumento como TRUE retorna o valor último .

Isto é em grande parte não documentado e obscuro, mas data do VisiCalc (1979) e hoje é válido pelo menos no Microsoft Excel, no LibreOffice Calc e no Google Sheets. Em última análise, é devido à implementação inicial de LOOKUP no VisiCalc (e daí VLOOKUP e HLOOKUP ), quando não havia um quarto parâmetro. O valor é encontrado por pesquisa binária , usando o limite esquerdo e exclusivo inclusivo (uma implementação comum e elegante), que resulta neste comportamento.

Tecnicamente, isso significa que inicia-se a pesquisa com o intervalo de candidatos [0, n) , em que n é o comprimento da matriz e a condição invariante de loop é A[imin] <= key && key < A[imax] (o limite esquerdo é < = o destino , o direito, que inicia um após o final, é > o alvo; para validar, ou verificar os valores nos pontos finais antes, ou verificar o resultado após), e dividir sucessivamente e escolher o lado que preserva essa invariante: por exclusão um lado , até chegar a um intervalo com 1 termo, [k, k+1) , e o algoritmo retorna k . Isso não precisa ser uma correspondência exata (!): É apenas a correspondência mais próxima de baixo. No caso de correspondências duplicadas, isso resulta no retorno da correspondência último , já que requer que o próximo valor seja maior do que a chave (ou o fim da matriz). No caso de duplicatas, você precisa de um comportamento alguns , e isso é razoável e fácil de implementar.

Esse comportamento é declarado explicitamente neste artigo antigo da Microsoft Knowledge Base (ênfase adicionada): "XL: Como retornar a primeira ou a última correspondência em uma matriz" ( Q214069 ):

You can use the LOOKUP() function to search for a value within an array of sorted data and return the corresponding value contained in that position within another array. If the lookup value is repeated within the array, it returns the last match encountered. This behavior is true for the VLOOKUP(), HLOOKUP(), and LOOKUP() functions.

A documentação oficial para algumas planilhas segue; Em nenhum deles o comportamento da "última correspondência" é indicado, mas está implícito na documentação do Planilhas Google:

  • Microsoft Excel

    TRUE assumes the first column in the table is sorted either numerically or alphabetically, and will then search for the closest value.

  • Planilhas Google :

    If is_sorted is TRUE or omitted, the nearest match (less than or equal to the search key) is returned

por 26.01.2016 / 07:05
1

Se os valores na matriz de pesquisa forem sequenciais (ou seja, você está procurando o maior valor, como a data mais recente), nem precisa usar a função INDIRETO. Experimente este código simples:

=MAX(IF($A$1:$A$20="c",$B$1:$B$20,)

Novamente, insira a fórmula usando CTRL + SHIFT + ENTER

    
por 18.03.2016 / 00:37
0

Eu experimentei o valor mais frequente. Não tenho certeza se funcionaria no libreOffice, mas parece funcionar no excel

=INDEX($B$2:$B$9,MATCH(MAX(--($A$2:$A$9=D2)*COUNTIFS($B$2:$B$9,$B$2:$B$9,$A$2:$A$9,D2)),--($A$2:$A$9=D2)*COUNTIFS($B$2:$B$9,$B$2:$B$9,$A$2:$A$9,D2),0))

A coluna A seria o beneficiário, a coluna B seria a categoria, D2 seria o beneficiário pelo qual você deseja filtrar. Não sei por que está colocando quebra de linha extra na função acima.

Minha função para encontrar a última célula seria a seguinte:

=INDIRECT("B" & MAX(--($A$2:$A$9=D2)*ROW($A$2:$A$9)))

Indireto me permite especificar a coluna que desejo retornar e encontrar a linha diretamente (portanto, não preciso subtrair o número de linhas de cabeçalho.

Essas duas funções precisam ser inseridas usando Ctrl + shift + enter

    
por 11.07.2014 / 21:58
0
=LOOKUP([payee field] , [payee range] , [category range])

Isso vai te dar o último valor

Recebo pontos de bônus por estar 3 anos atrasado?

    
por 07.09.2017 / 23:32
-1

Você recebeu #DIV/0! de erros porque prefere escrever sua fórmula como:

=LOOKUP(2;IF(([payee range] = [search value]);1;"");[category range])

isso funcionará e encontrará a última correspondência.

([payee range] = [search value]) : matriz booleana TRUE / FALSE

IF(([payee range] = [search value]);1;"") : matriz pseudo-booleana 1 / ""

=LOOKUP(2; {pseudo-boolean matrix 1/""} );[category range]) : sempre retornar último 1 posição

    
por 24.09.2015 / 12:18