2011-07-19 67 views
12

我想用查找或类似的功能来搜索工作表,匹配帐号,然后返回指定的值。我的问题是有重复的帐户号码,我想结果连接到一个字符串的结果。excel与多个结果的查找

Acct No CropType 
------- --------- 
0001  Grain 
0001  OilSeed 
0001  Hay 
0002  Grain 

是在第一个工作表,第二个工作表上我有没有会计与其他信息,我需要得到所有的匹配结果为一列2号表即。 “谷物油籽干草”

+1

+1容易理解的第一个问题:) – ChrisO

回答

7

这是一个可以帮你做的功能。这与Vlookup有一点不同,因为您只会将它列入搜索列,而不是整个范围,然后作为第三个参数,您会告诉它需要向左(负数)还是向右(正数)移动多少列才能获得你的回报价值。

我还添加了使用分隔符的选项,在您的情况下您将使用“”。下面是函数调用你的,假设第一排,科目编号为A,结果是B行:

=vlookupall("0001", A:A, 1, " ") 

下面是函数:

Function VLookupAll(ByVal lookup_value As String, _ 
        ByVal lookup_column As range, _ 
        ByVal return_value_column As Long, _ 
        Optional seperator As String = ", ") As String 

Dim i As Long 
Dim result As String 

For i = 1 To lookup_column.Rows.count 
    If Len(lookup_column(i, 1).text) <> 0 Then 
     If lookup_column(i, 1).text = lookup_value Then 
      result = result & (lookup_column(i).offset(0, return_value_column).text & seperator) 
     End If 
    End If 
Next 

If Len(result) <> 0 Then 
    result = Left(result, Len(result) - Len(seperator)) 
End If 

VLookupAll = result 

End Function 

注:

  • 如果您不输入结果,我将“,”作为结果的默认分隔符。
  • 如果有一个或多个命中,我在最后添加了一些检查 确保字符串不以一个额外的分隔符结束。
  • 我已经使用A:A作为范围,因为我不知道你的范围,但是 显然如果你输入实际的范围会更快。
+0

作品太棒了!不幸的是,它需要很长的时间:( – javydreamercsw

+0

绝对不是一个好主意,通过这个代码传递一个无界的范围。如果你传递A:A这里的例子,代码将检查所有1,048,576行每次运行。输入一个实际的范围,而不是传入整列。 – Jesse

+0

@aevanko使用WorksheetFunction.CountA(lookup_column)来计数,它更快! –

2

一种方式做,这是使用数组公式的所有比赛的填充到一个隐藏列,然后串联这些值到你的字符串显示:

=IFERROR(INDEX(cropTypeValues,SMALL(IF(accLookup=accNumValues,ROW(accNumValues)-MIN(ROW(accNumValues))+1,""),ROW(A1))),"") 
  • cropTypeValues:命名范围包含作物类型的列表。
  • acc查看:命名范围包含查找的帐号。
  • accNumValues:命名范围持有您的帐户列表 数字。

输入为数组公式(Ctrl + Shift + Enter),然后按需要复制下来。

让我知道你是否需要解释公式的任何部分。

+0

这是我的首选解决方案,因为它避免了宏同住时,可以得到禁止。这对于无限数量的比赛来说并不理想,但如果你只希望少数几场比赛,那很好。 https://www.extendoffice.com/documents/excel/2699-excel-vlookup-find-first-2nd-match.html给出了很好的例子。 – beldaz

0

我刚刚有一个类似的问题,我已经查了很长一段时间类似的解决方案,但没有真正说服我。要么你必须编写一个宏或者一些特殊的函数,但是为了我的需要,最简单的解决方案是在例如数据库中使用一个数据透视表。 Excel中。

如果您从数据创建新的数据透视表,并首先将“Acct No”添加为行标签,然后将“CropType”添加为RowLabel,那么您将拥有一个非常好的分组,可为每个帐户列出所有的作物类型。尽管如此,它不会在单个单元中实现。

-1
Function VLookupAll(vValue, rngAll As Range, iCol As Integer, Optional sSep As String = ", ") 
    Dim rCell As Range 
    Dim rng As Range 
    On Error GoTo ErrHandler 
    Set rng = Intersect(rngAll, rngAll.Columns(1)) 
    For Each rCell In rng 
     If rCell.Value = vValue Then 
      VLookupAll = VLookupAll & sSep & rCell.Offset(0, iCol - 1).Value 
     End If 
    Next rCell 
    If VLookupAll = "" Then 
     VLookupAll = CVErr(xlErrNA) 
    Else 
     VLookupAll = Right(VLookupAll, Len(VLookupAll) - Len(sSep)) 
    End If 
ErrHandler: 
    If Err.Number <> 0 Then VLookupAll = CVErr(xlErrValue) 
End Function 

使用这样的:

=VLookupAll(K1, A1:C25, 3)

查找K1的值的所有出现在范围A1:A25,并返回从列C的相应值,以逗号分隔。

如果要进行求和值,则可以使用SUMIF,例如

=SUMIF(A1:A25, K1, C1:C25)

在C1至求和值:C25其中在列A中的相应值等于K1的值。

ALL D BEST。

0

这里是我的代码比一个Excel VLOOKUP甚至更好,因为你可以选择criterie科拉姆,而且可以肯定的隔板(Carriege返回太多)...

Function Lookup_concat(source As String, tableau As Range, separator As String, colSRC As Integer, colDST As Integer) As String 
    Dim i, y As Integer 
    Dim result As String 

    If separator = "CRLF" Then 
     separator = Chr(10) 
    End If 

    y = tableau.Rows.Count 
    result = "" 
    For i = 1 To y 
     If (tableau.Cells(i, colSRC) = source) Then 
      If result = "" Then 
       result = tableau.Cells(i, colDST) 
      Else 
       result = result & separator & tableau.Cells(i, colDST) 
      End If 
     End If 
    Next 
    Lookup_concat = result 
End Function 

而且礼物,可以使还可以查看同一单元格的多个元素(基于相同的分隔符)。真正有用的

Function Concat_Lookup(source As String, tableau As Range, separator As String, colSRC As Integer, colDST As Integer) As String 
    Dim i, y As Integer 
    Dim result As String 

    Dim Splitted As Variant 

    If separator = "CRLF" Then 
     separator = Chr(10) 
    End If 

    Splitted = split(source, separator) 

    y = tableau.Rows.Count 
    result = "" 
    For i = 1 To y 
     For Each word In Splitted 
      If (tableau.Cells(i, colSRC) = word) Then 
       If result = "" Then 
        result = tableau.Cells(i, colDST) 
       Else 
        Dim Splitted1 As Variant 
        Splitted1 = split(result, separator) 
        If IsInArray(tableau.Cells(i, colDST), Splitted1) = False Then 
         result = result & separator & tableau.Cells(i, colDST) 
        End If 
       End If 
      End If 
     Next 
    Next 
    Concat_Lookup = result 
End Function 

上一页子需要此功能

Function IsInArray(stringToBeFound As String, arr As Variant) As Boolean 
    IsInArray = (UBound(Filter(arr, stringToBeFound)) > -1) 
End Function