Excel公式或VBA:使用2列标准在单独的表中查找匹配的地址 - 无帮助列

sou*_*ned 2 excel vba formula excel-vba excel-formula

我需要有关配方结构的帮助,

我有2张桌子.我想找到一个匹配,其中列a和列b相等,并获得表2中的地址.它们将是唯一条目.例如:

ProjectInfoTable:

         A      |       B      |     C     |
  ------------------------------------------
1 |     Name    |    Company   |  Project  |
  ------------------------------------------
2 | Chris Evans |     Apple    |   Info    |
  ------------------------------------------
3 | Chris Evans |    Google    |   Info    |
  ------------------------------------------
4 | Bill Gates  |  Burger King |   Info    |
  ------------------------------------------
Run Code Online (Sandbox Code Playgroud)

ClientInfoTable:

         A      |       B      |   C   |   D
  -------------------------------------------
1 |    Client   |    Company   |  Age  |  Sex | 
  -------------------------------------------
2 | Chris Evans |     Apple    |   12  |   M  |
  -------------------------------------------
3 | Chris Evans |    Google    |   17  |   M  |
  -------------------------------------------
4 | Bill Gates  |  Burger King |   98  |   F  |
  -------------------------------------------
Run Code Online (Sandbox Code Playgroud)

我希望能够在'ProjectInfoTable'中获取'ClientInfoTable'中匹配的Name&Company客户端的地址

我遇到的麻烦是那里可能有一千个不同的Chris Evans,所以VLOOKUP在这里并不好.我需要通过交叉引用他们的公司来确保我在"ProjectInfoTable"中看到的"ClientInfoTable"中的Chris Evans

如果我只按名称搜索,我可以得到地址没问题:

=ADDRESS(ROW(INDEX(ClientInfoTable,MATCH([@[Client]],ClientInfoTable[Client],0),1)),COLUMN(INDEX(ClientInfoTable,MATCH([@[Client]],ClientInfoTable[Client],0),1)),1,1,"Clients")
Run Code Online (Sandbox Code Playgroud)

但我需要增加他们公司的附加条件,所以现在公式是无用的.

有什么想法吗?我不想使用隐藏列或'帮助列'

我将除了VBA或基于公式的答案.我甚至会奖励赏金的人谁可以同时提供,假设数据永远是动态范围,并且然后给出你的代码/公式的一个很好的解释.我在这里学习,我不是一个复制/粘贴类型的用户,解释与我很长.

Rob*_*zie 7

式:

这是一个只有公式的解决方案,没有隐藏/帮助列,也没有数组公式:

=ADDRESS(
    ROW(
        ClientInfo
    ) - 1 +
    MATCH(
        1,
        INDEX(
            --INDEX(
                ClientInfo[Client] = $A5,
                0
            ) *
            --INDEX(
                ClientInfo[Company] = $B5,
                0
            ),
            0
        ),
        0
    ),
    COLUMN(ClientInfo)
)
Run Code Online (Sandbox Code Playgroud)

组件:

a --INDEX(ClientInfo[Client]=$A5,0) - 为例如Chris Evansin中的多个匹配返回一个布尔数组ClientInfo[Client].在下面的例子中,这将是{TRUE,TRUE,FALSE,FALSE}.然后将其转换为整数数组,并使用双一元运算符离开{1,1,0,0}

b --INDEX(ClientInfo[Company]=$B5,0) -同样的事情,一个例如AppleClientInfo[Company]在例子是阵列{TRUE,FALSE,FALSE,TRUE}-其然后浇铸到{1,0,0,1}

c INDEX(a*b,0) - 数组a的元素1..n的倍数与数组b的元素1..n .在我们的示例中,这导致{1,0,0,0} 并且此时您已将Chris Evans和Apple的匹配组合键标识为ClientInfo的第一行

d MATCH(1,c,0) - 获取数组中1的索引,在我们的例子中,Chris Evans和Apple是1.你提到它们将是唯一的条目,所以我认为我们在这里没有问题.

e ROW(ClientInfo)-1+d - 我定义ClientInfo为一个Table/ListObject,其范围是一个A8:D12但是引用是回馈的A9:D12,它似乎是它对Tables/ListObjects的命名范围起作用的方式.因此,我们需要从该ROW范围中扣除一个以获得偏移的开始; 然后简单地添加d的结果.

f ADDRESS(e,COLUMN(ClientInfo)) - 返回e的单元格地址和ClientInfo表格的第一列.

例:

在此输入图像描述

VBA:

使用上面的示例,VBA方法将执行以下操作:

  1. 假设找不到匹配项
  2. 迭代表的行
  3. 获取候选值并检查引用列的输入
  4. 如果两者都匹配则退出循环返回地址

代码:

Option Explicit

Sub Test()

    MsgBox GetAddressOfKey("Client", "Chris Evans", "Company", "Apple", "ClientInfo")
    MsgBox GetAddressOfKey("Client", "Chris Evans", "Company", "Google", "ClientInfo")
    MsgBox GetAddressOfKey("Client", "Bill Gates", "Company", "Burger King", "ClientInfo")

End Sub

Function GetAddressOfKey(col1 As String, val1 As String, col2 As String, val2 As String, strTable As String) As String

    Dim lst As ListObject
    Dim lr As ListRow
    Dim strAddress As String
    Dim strCandidate1 As String
    Dim strCandidate2 As String

    strAddress = ""
    Set lst = ActiveSheet.ListObjects(strTable)

    'iterate rows
    For Each lr In lst.ListRows
        'get candidate values
        strCandidate1 = Intersect(lr.Range, lst.ListColumns(col1).Range).Value
        strCandidate2 = Intersect(lr.Range, lst.ListColumns(col2).Range).Value
        'check against inputs
        If strCandidate1 = val1 And strCandidate2 = val2 Then
            strAddress = lst.Range.Cells(lr.Index + 1, 1).Address
            'quit if we find a match
            Exit For
        End If
    Next lr

    'return
    GetAddressOfKey = strAddress

End Function
Run Code Online (Sandbox Code Playgroud)

PS我对提供VBA答案犹豫不决,你已经接受了一个不错的答案.但是,我稍微倾向于在不更新UI的情况下这样做,尽管我同意这种AutoFilter方法已经足够了.HTH