ユーザー定義関数で辞書のような使用法

このQ&Aのポイント
  • ユーザー定義関数を使用して、指定したフォルダ内のエクセルファイルから文字列を引っ張る方法について説明します。
  • Vlookup関数のような形で引っ張ってくることができますが、ファイルパスを指定することができない場合の解決方法についても検討します。
  • ファイルをOpenしても解決できず、どうすればいいかについてもお伝えします。
回答を見る
  • ベストアンサー

ユーザー定義関数で辞書のような使用法

Excel2000ユーザー定義関数で、 参照された文字列を、任意のフォルダ内にあるエクセルファイルから、 Vlookup関数のような形で引っ張ってくることは出来るでしょうか? どうしても、ファイルパスを指定出来ません。 ex) Function kanjiname(セル) Application.Volatile Dim myRange As Range Set myRange = Workbooks("C:\辞書ファイル.xls").Worksheets("Sheet1").Range("C1:C9") kanjiname = Application.VLookup(セル, myRange, 5, False) という感じにしたいのです。 開いていないファイルをOpenしても無理ですし、 どうすればいいのでしょうか。 End Function

質問者が選んだベストアンサー

  • ベストアンサー
  • KenKen_SP
  • ベストアンサー率62% (785/1258)
回答No.3

=VLOOKUP(RC[-1],'C:\[辞書ファイル.xls]Sheet1'!C1:C9,5,FALSE) #1の方もコメントされてますが、この計算式は正しい値を返しません。 というツッコミは横においておきます。 >アドインの中にそのようなデータベースを蓄積させる方法は無いものでしょうか。。 この方法は、#1でも「さらっ」と書いてますが、ほぼ同じことを延べた手法ですよ。 VLOOKUP関数でデータを検索しているブックを便宜上A.xlsとしましょう。 1. A.xls に新規シートを追加し、シート名を DataSheet とします 2. C:\辞書ファイル.xls を開きます 3. C:\辞書ファイル.xls の Sheet1 の C1:C9 をコピーします 4. A.xls の 1で追加したシート DataSheet の C1セルを選択   [形式を指定して貼付け]から[リンク貼付け]をクリックします   -->C:\辞書ファイル.xls の内容が表示されます。 これで、計算式は、 =VLOOKUP(RC[-1],DataSheet!C1:C9,... と同一ブックの参照で計算式が書けますね。VLOOK関数内で他ファイルを指定するのは(これができたかどうか確かめてませんが)、関数が再計算のたび閉じたブックのデータを取得しに行くわけですから、時間がかかって当然です。 そこで、作業シートにリンクを張ってデータを取り込む。これは、ブックを開いたときに「更新しますか?」と聞かれて、その後は参照しません。つまり、始めに一気にデータを取り込こんでおくわけです。 作業シートに C:\辞書ファイル.xls のデータをリンクさせておいて、VLOOKUP関数で参照するのは 作業シート。です。 とまぁ、、ここまで言ってなんですが、、 C:\辞書ファイル.xls のシートを A.xls にコピーするのはダメなんですか?

その他の回答 (2)

  • KenKen_SP
  • ベストアンサー率62% (785/1258)
回答No.2

>開いていないエクセルファイルから... ブックを開かず開かずデータを取得する方法はバイナリ解析、またはADOやDAOでデータベース接続するしかありません。これは、難易度が高いです。 ブックを開いていないように見せかけてデータを取得する方法は、Application.ScreenUpdating で画面更新を停止して、ブックを開き、データ取得後、ブックを閉じてしまえばOKです。または、EXCEL4.0マクロを使用します。 ここで、今回ご希望の処理について考えて見ます。 結論から言えば、ユーザー定義関数で処理するのはお勧めできません。 上記の方法でデータさえ拾えれば、ご希望通りの関数は作成可能は可能ですが、関数が再計算される度に、“ブックのOPEN/CLOSE”や“データ問合せ”を繰り返すわけですから、アっという間にフリーズするかも知れないです。さらに、Application.Volatile でやるなら、なおさらです。 今回は、作業シートに作り、辞書ファイル.xlsからのリンクを張って、そこをVLOOKUPで検索すれば良いかと思います。また、作業シートは非表示にしておけば良いと思います。 最後に一応、“ブックを開いていないように見せかけて”データを取得する関数のサンプルコードをアップしておきます。 '【WorkBookを見かけ上開かず指定シート+指定セルのデータを配列で返す】 Function GetData( _   strBookPath As String, _   strSheetNam As String, _   strCellAddr As String)      Dim Wb As Workbook   Dim Sh As Worksheet   Dim Buf      On Error GoTo ErrorHandler   Application.ScreenUpdating = False   Set Wb = Workbooks.Open(strBookPath, , True)   Set Sh = Wb.Sheets(strSheetNam)   GetData = Sh.Range(strCellAddr).Value    ExitHandler:   Wb.Close   Set Sh = Nothing   Set Wb = Nothing   Exit Function ErrorHandler:   GetData = False   Resume ExitHandler End Function 【使い方】 配列変数=GetData(ブックのフルパス,シート名,セルアドレス) Sub Sample()   Dim myData As Variant      myData = GetData("C:\TEST.xls", "Sheet1", "A1:E4")   If IsArray(myData) = False Then     MsgBox "データ取得に失敗", vbCritical     Exit Sub   Else     ActiveSheet.Range("A1") _     .Resize(UBound(myData), UBound(myData, 2)) = myData   End If End Sub

thisis2wakei
質問者

お礼

なるほど。 いろいろ調べたのですが、あまり的を得たtextが無かったもので、、、そういう時は、できないという事ですね。 現在は、IMEでnameを変換すると、「=VLOOKUP(RC[-1],'C:\[辞書ファイル.xls]Sheet1'!C1:C9,5,FALSE)」 と変換されるように設定し、使用しているんですが、時間がかかって… 結局同じように時間がかかるということなんですね。 アドインの中にそのようなデータベースを蓄積させる方法は無いものでしょうか。。

  • maruru01
  • ベストアンサー率51% (1179/2272)
回答No.1

こんにちは。maruru01です。 根本的な解決にはならないかも知れないし、単なる記載ミスかも知れませんが、1点だけ。 myRangeの範囲が「C1:C9」ということは、VLookup関数の第3引数に「5」は指定出来ないのでは? 「C1:G9」のように最低5列は必要かと思いますが。

関連するQ&A

  • VBAの関数について

    VBA初心者です。 VLOOKUP関数の使い方がわかりません。 具体的に書かせてもらうと VBAの中にVLOOKUP関数を使いたいです 試験1ファイルのシート"sheet1"にある 検索値を使い 試験2ファイルの指定した検索範囲を 試験1ファイルのシート"sheet1"の指定した位置に数値を挿入することです。 例えばですが(この使い方も間違ってるかもしれません)コードを書いてみると 試験1の検索値はA5セルとします 試験2の検索範囲はB1~C20とします 検索範囲から取得した数値の位置はD5とします VLOOKUPに関してですが 検索値は変数を使い 検索値範囲も変数を使い 列番号はC列がいいので3で 検索方法はFALSEでお願いします sub test() dim a as range dim b as workbooks dim c as range set a = range("B1~C20") set b = workbooks("sheet1") set c = range("A5") workbooks("試験1").worksheets("sheet1").range("D5").value=workbooks("試験2").activesheet."=VLOOKUP(ここがわかりません)".value end sub そもそも変数やsetの使い方が間違ってるかもしれませんm(__)m コードを書いて貰えるととても助かります。 回答お願いします。

  • エクセルVBA IDの有無をユーザー定義関数で知る方法

    Sheet1上のA1セルにIDプロパティでのIDを設定した場合、これをワークシート関数で取得する方法が見つけられなかったのでユーザー定義関数を以下の通り作成しました。 Function IDCheck(CksCell As Range) As Boolean Application.Volatile (True) IDCheck = Sheets("Sheet1").Range(CksCell.Address).ID <> "" End Function これで、Sheet1上で=IDCheck(A1) というように記述すれば、IDが設定してあればTRUE、そうでなければFALSEを返すのでわかります。 ところが、このままでは自動計算のつもりでApplication.Volatile (True)を記述しているにもかかわらず、IDを削除してもワークシート上の表示はTRUEのままです。 どうしたらよいのでしょうか? もし、ワークシート関数で取得する方法があれば、そちらの方がベターです。

  • マクロをすっきりさせたい・・・

    いつもお世話になっております。 下記、マクロを組んだのですが、 簡潔にまとめるには、どうしたら良いでしょうか・・・ 宜しくお願い致します。 Set 範囲 = Workbooks("A.xls").Worksheets("マスター").Range("A2:G4000") ThisWorkbook.Activate 列番号 = 7 検索値 = (Worksheets("B").Range("B24")) Range("D14").Value = WorksheetFunction.VLookup(検索値, 範囲, 列番号, False) Set 範囲 = Workbooks("A.xls").Worksheets("マスター").Range("A2:G4000") ThisWorkbook.Activate 列番号 = 7 検索値 = (Worksheets("B").Range("B25")) Range("D15").Value = WorksheetFunction.VLookup(検索値, 範囲, 列番号, False) Set 範囲 = Workbooks("A.xls").Worksheets("マスター").Range("A2:G4000") ThisWorkbook.Activate 列番号 = 7 検索値 = (Worksheets("B").Range("B26")) Range("D16").Value = WorksheetFunction.VLookup(検索値, 範囲, 列番号, False)

  • vba 自作関数

    Function zei(myRng As Range) As Double Dim c As Range Dim goukei As Double 'Volatileについて 'シート内のどこかのセルを参照しているものとする 'シートのどこかに変更があったらそのセルが自動的に再計算される Application.Volatile goukei = Application.WorksheetFunction.Sum(myRng) zei = Int(goukei * 5 / 100) End Function これを標準モジュールに貼り付けてワークシート上で関数を呼び出し、 100を入れると#VALUE!が返るのですがどうしてでしょうか? 違う値を入れても必ず#VALUE!が返ります。

  • ユーザ定義関数がうまく動きません。

    ユーザ定義関数がうまく動きません。 2月のA1セル値が1になっていたりします。 どこがおかしいのかわかりません。解決方法を教えていただけませんでしょうか。 よろしくお願いします。 【シートの設定】 シート名は1月・・・12月です。 各シートの A1セルは「=sheetname()」 B1セルは「月のチェックシート」 が入っています。 【VBAの設定】 Function SheetName() As String 'Application.Volatile If Len(ActiveSheet.Name) = 3 Then SheetName = Left(ActiveSheet.Name, 2) Else SheetName = Left(ActiveSheet.Name, 1) End If End Function

  • (EXCEL)関数に関数を組み込む方法

    例えば、VLOOK関数で、VLOOKUP(A1,'[aaa.xls]4月'!A1:C25,3,false)とした場合は、上手く動くとします。 次に、仮にA2セルに「[aaa.xls]4月'!A1:C25」と入力しておき、VLOOKUP(A1,A2,3,false)とすると上手く動きません(エラーになります) A2に「[aaa.xls]4月'!A1:C25」と入れた状態で、それを利用してVLOOKUP関数を使おうとした場合、どのようにすればいいでしょうか? どうして上記のようなことをしようとしているかというと、「aaa.xls」のシートが月ごとに分かれてしまっているからです。 別ブックで日を入れると対応するセル値を引っ張ってきたいんですが、以下のように設定しました。 VLOOKUP(A1,"'[aaa.xls]"&MONTH(A2)&"月'!A1:C25",3,false) しかし、"'[aaa.xls]"&MONTH(A2)&"月'!A1:C25"の部分が認識されず、エラーとなってしまいます。 どのように直せばよろしいでしょうか?

  • エクセル 複数シート( VLOOKUP ユーザー定義関数

    複数シート(範囲)を指定できるVLOOKUP関数をユーザー定義で作りたいと思ってます。下記のコードではうまく動かないので教えてください。 Function VLOOKUPM(検索値 As Variant, 対象シート As String, 対象セル As Range, 列番号 As Integer) As Variant Dim i As Integer Dim r As Range Dim sh As Variant Application.Volatile sh = Split(対象シート, ",") For i = 0 To UBound(sh) Set r = Sheets(sh(i)).Range(対象セル) If 検索値 = r Then VLOOKUPM = r.Offset(0, 列番号) Exit Function End If Next End Function

  • ユーザー定義関数にて

    色つきセルの合計を数えるユーザー定義関数を使用していますが 普通の関数のように、セルに変更等ですぐに更新してくれればいいのですが 表示は前回のままです。(ですのでF9を押しています) 計算ではちゃんとした数字になっているのですが 更新が遅くて変更されません。 (セル範囲は縦で30個ぐらいです) すぐに更新するいい方法はないでしょうか? ご経験者の方々、知識ある方々の ご意見やアドバイスなどをよろしくお願いします。 色つきセルのカウント Function CountColor(計算範囲, 条件色セル) Application.Volatile CountColor = 0 For x = 1 To 計算範囲.Rows.Count If 計算範囲.Rows(x).Interior.ColorIndex = 条件色セル.Interior.ColorIndex Then CountColor = CountColor + 1 End If Next End Function

  • ユーザー定義関数をボタンに登録したい

    数式のエラーを回避するユーザー定義関数を作りPERSONAL.xlsに登録しました。 その後アドインに保存して、関数の挿入ダイアログボックスのユーザー定義関数から選んで使用していますが、頻繁に使用するのでボタンに登録したいのです。 どのようにすればいいのでしょうか? ネットで検索して色々やってみてるのですが分かりません。 ボタンのマクロの登録で「PERSONAL.xla!vlookupエラー回避」と直接打ち込んで登録してみましたが、実際にボタンをクリックすると「コンパイルエラー End Subが必要です」というエラーメッセージが出ます。 どこをどうすればいいのか教えてください。よろしくお願いします。 Sub vlookupエラー回避() ' ' vlookupエラー回避 Macro ' マクロ記録日 : 2006/7/25 ユーザー名 : ******** ' Function myVLookup(Rg As Range, Area As Range, col As Integer, opt As Integer) Dim vlk As Variant vlk = Application.VLookup(Rg, Area, col, opt) If IsError(vlk) Then vlk = "" End If myVLookup = vlk End Function

  • エクセルマクロ if文を繰り返したい

    マクロ初心者です。 以下のようなマクロを作ったのですが、 これをE34まで繰り返しの処理をしたいです。 どこにどんな文章を挟んでいいのかわかりません。 Sub けいさん() If Workbooks("日報.xls").Worksheets("お手本").Range("O22") = "A" Then Workbooks("test.xls").Worksheets("II-1(1)").Range("E11") = "" ElseIf Workbooks("日報.xls").Worksheets("お手本").Range("O22") = "B" Then Workbooks("test.xls").Worksheets("II-1(1)").Range("E11") = "" ElseIf Workbooks("日報.xls").Worksheets("お手本").Range("O22") = "D" Then Workbooks("test.xls").Worksheets("II-1(1)").Range("E11") = "" ElseIf Workbooks("日報.xls").Worksheets("お手本").Range("C22") = "" Then Workbooks("test.xls").Worksheets("II-1(1)").Range("E11") = "" Else Workbooks("日報.xls").Worksheets("お手本").Range("C22").Copy Workbooks("test.xls").Worksheets("II-1(1)").Range("E11").PasteSpecial End If End Sub

専門家に質問してみよう