web-dev-qa-db-ja.com

Excel数式で動的名前付き範囲を参照する

ブックの他の場所にある動的な名前付き範囲の一部に対応する列見出しを持つExcelのテーブルがあります。たとえば、「10」、「20」などの列見出しと、「NameRange10」、「ExampleRange2」などの動的な名前付き範囲があります。連結して、ExampleRange10を参照するVLookup式を入力します文字列「ExampleRange」と列見出し「10」。これにより、各列の数式に「ExampleRange10」、「ExampleRange20」などを手動で入力する代わりに、テーブルのすべての列に数式を単純に拡張できます。

私はINDIRECT関数を認識しており、過去に名前付き範囲で正常に使用したことがありますが、この場合はdynamic名前付き範囲では機能していないようです。 。これは、動的な名前付き範囲がExcelでどのように定義されるかに関係していると思います(数式バーの左側にある名前付き範囲のドロップダウンには表示されず、VBAにいくつかの興味深いプロパティがあります、 例えば)。動的な名前付き範囲と組み合わせてINDIRECT数式を使用する方法はありますか、それともこの問題を解決する別の方法がありますか?

編集:使用されている正確な式は次のとおりです。
これは主な式です:=VLOOKUP(B2,INDIRECT("ExampleRange"&C1),2,FALSE)ここで、C1には「10」が含まれ、「ExampleRange10」と呼ばれる動的な名前付き範囲の式は=OFFSET(Sheet1!$F$2,0,0,COUNTA(Sheet1!$F$2:$F$25),2)です。メインの数式は「#REF!」を返しますが、動的な名前付き範囲の数式を削除し、「ExampleRange10」を静的な範囲として定義すると正しく機能します。

8
Kyle Wurtz

さらに調査を行った後でわかるように、ExcelのINDIRECT関数はダイナミックレンジでは機能しません。 INDIRECTを使用してVBA以外のExcelの世界にこだわる賢い方法があるかもしれませんが、私はそのような方法を知りません。代わりに、記述されたものと非常によく似たユーザー定義関数を作成しました here 。メインの数式を=VLOOKUP(B2,DINDIRECT("ExampleRange"&C1),2,FALSE)に変更しました。ここで、DINDIRECTは作成したVBA関数の名前です。

この代替方法の唯一の欠点(見方によっては欠点になる場合とそうでない場合があります)は、ブックをマクロ対応のブックとして保存する必要があり、カスタム関数の使用があまり自己文書化されていないことです。他のユーザーへの少しの説明が必要です。とはいえ、すべてが考慮されましたが、これは私にとって許容できる解決策でした。

Link-averseのコードは次のとおりです。

Public Function DINDIRECT(sName As String) As Range
     Dim nName As Name

     On Error Resume Next
          Set nName = ActiveWorkbook.Names(sName)
          Set nName = ActiveSheet.Names(sName)
     On Error GoTo 0

     If Not nName Is Nothing Then
          Set DINDIRECT = nName.RefersToRange
     Else
          DINDIRECT = CVErr(xlErrName)
End Function

注:この解決策は機能しましたが、他の人がより良い解決策を投稿するのを思いとどまらせたくないので、私の答えを受け入れるつもりはありません。また、私はこのサイトを初めて使用するので、自分の質問に答えてエチケットコードを壊してしまった場合は、申し訳ありません...他の人が役立つと思った場合に使用した正確な解決策を共有したいと思いました.

6
Kyle Wurtz

私は最近この正確なレンガの壁にぶつかりました。すでに推測したとおり、答えは動的な名前付き範囲をINDIRECTで参照できないことです。

ただし、ダイナミックレンジの式itselfをINDIRECTの引数として使用できますが、これはやりたいことには役に立ちません。非常に役立つ種類の機能であるため、PITAとは多少異なります。

5
blackworx

データに10、20などのヘッダーがある場合は、Indirectを使用する必要はありません。インデックス/マッチを使用して必要なデータを選択しないのはなぜですか?

たとえば、テーブル全体にExampleRangesという名前を付け、次の式を使用します。

Index(ExampleRanges, match(B2, index(ExampleRanges, , 1), 0), match(C1, index(ExampleRanges, 1,), 0))
1
Cool Blue

テストされていませんが、これでうまくいくと思います。

動的に名前が付けられた範囲のアドレスを返すユーザー定義関数:

Function Named_Range_Address(Range_Name As Range, _ 
    Optional SheetName As Boolean) As String 

    Dim strName As String 
    Application.Volatile 

    If SheetName = True Then 
        strName = "'" & Range_Name.Parent.Name & "'!" & Range_Name.Address 
    Else 
        strName = Range_Name.Address 
    End If 

    Named_Range_Address = strName 
End Function 

次に、vlookup式を使用できるようになります。

=VLOOKUP(B2,INDIRECT(named_range_address("ExampleRange"&C1,TRUE)),2,FALSE)
0
scott

私はこれが本当に古いスレッドであることを知っていますが、私は同じ問題を抱えていたので、おそらく私の解決策は将来人々を助けることができます。

基本的に、保存時に範囲を削除して再定義し、名前を付けるマクロを作成しました。したがって、範囲が動的ではなかったため、INDIRECT関数は機能します。名前付き範囲に値を追加した後、ワークブックを保存するだけです。

Private Sub Workbook_BeforeSave(ByVal SaveAsUI As Boolean, Cancel As Boolean)

Dim a, b, c, d, e, f As Integer
Dim data As Worksheet

Set data = ThisWorkbook.Worksheets("Data")

a = data.Range("A" & Rows.count).End(xlUp).row
b = data.Range("B" & Rows.count).End(xlUp).row
c = data.Range("C" & Rows.count).End(xlUp).row
d = data.Range("D" & Rows.count).End(xlUp).row
e = data.Range("E" & Rows.count).End(xlUp).row
f = data.Range("F" & Rows.count).End(xlUp).row



ActiveWorkbook.Names("KP").Delete
ActiveWorkbook.Names("KPT").Delete
ActiveWorkbook.Names("AP").Delete
ActiveWorkbook.Names("APT").Delete
ActiveWorkbook.Names("DISC").Delete
ActiveWorkbook.Names("SEATS").Delete

ActiveWorkbook.Names.Add Name:="KP", RefersTo:="=Data!$A$2:$A$" & a
ActiveWorkbook.Names.Add Name:="KPT", RefersTo:="=Data!$B$2:$B$" & b
ActiveWorkbook.Names.Add Name:="AP", RefersTo:="=Data!$C$2:$C$" & c
ActiveWorkbook.Names.Add Name:="APT", RefersTo:="=Data!$D$2:$D$" & d
ActiveWorkbook.Names.Add Name:="DISC", RefersTo:="=Data!$E$2:$E$" & e
ActiveWorkbook.Names.Add Name:="SEATS", RefersTo:="=Data!$F$2:$F$" & f

End Sub
0
DavePenn

私はこれがかなり古いことを知っていますが、私はこれに出くわしたばかりで、これに遭遇した他の人を助ける場合に備えて、VBAコーディングを回避するソリューションを追加すると思いました:

=VLOOKUP(B2,CHOOSE(C1/10,example10,example20,example30,example40),2,0)

これは、命名規則が10、20、30などであることを前提としており、数百の範囲には理想的ではありません。

0
Dave

新しいひねりを加えると、アドレス関数と間接関数で名前付き範囲を使用することができます。一連のテーブルに名前付き範囲を設定していて、以下を使用している場合があります。

Named Range: WWDH-FF-PI which points to Linear!$A$19 (first cell in table)

アドレスを取得するには:$ T $ 56:= ADDRESS(MATCH(S56、Linear!A:A、0)、1,1,1、 "Linear")

次に、複数回コピーされたオフセット関数を使用して、ピボットテーブルを作成します。

=OFFSET(INDIRECT($T$56),C5,$T$57-1)

したがって、アドレス関数を間接関数に埋め込んで(またはラップして)、動的セルアドレスを作成できます。

0
rgo

今日、私はExcelの名前付き範囲をいじっていましたが、INDIRECT()呼び出し自体では範囲の名前を計算できないことは事実ですが、純粋な「Excel-」で取得できることを発見しました。中間ステップを追加することで「方法」:名前付き範囲を計算する非表示のセルを作成するだけです。

たとえば、_A1_に範囲名の「動的部分」が含まれているとし、_A2_で式_= "ExampleRange" & A1_を使用すると、使用できる完全な範囲名が得られます。 = INDIRECT(A2)として。

0