• 締切済み

Accessでの検索結果表示

Accessでの検索画面を作っているのですが *検索項目* ・顧客ID ・電話番号 ・氏名(前方一致で検索したい) *顧客テーブル* ・顧客ID ・電話番号 ・氏名 ・氏名カナ ・住所 3つを複合的な検索項目として、検索ボタンを押下した際に フォーム上のテキストボックスに顧客テーブルから 検索した住所を表示させたいと思っています。 現在、顧客コードだけを 検索項目として以下のようなコードを記述しているのですが これでさえもうまくいきません。 *************************** Dim cn As New ADODB.Connection Dim rs As New ADODB.Recordset Dim strRet As String Set cn = CurrentProject.Connection rs.Open "顧客テーブル", cn, adOpenKeyset, adLockOptimistic strRet = "顧客ID='" & Me!CustmID & "' " rs.Find strRet If Not rs.EOF Then Me.Address = rs!住所 Else: MsgBox "該当なし" End If rs.Close: Set rs = Nothing cn.Close: Set cn = Nothing End Sub **************************** 現状、何が悪いのかそしてどのようにこのプログラムを 改良すれば本来やりたいことができるのか 教えていただけますでしょうか。よろしくお願いいたします。

みんなの回答

  • CHRONOS_0
  • ベストアンサー率54% (457/838)
回答No.3

>クエリでは対応できないのかなと思っていますがいかがでしょうか。 確かに追加更新ができなくなるクエリというものもありますが 普通の選択クエリなら追加・更新は可能です 追加更新が不可になるケースについてはヘルプに詳しい説明がありますので 調べてみてください

  • CHRONOS_0
  • ベストアンサー率54% (457/838)
回答No.2

仕様に難ありですよ >・氏名(前方一致で検索したい) ということだと該当するものが複数というケースが考えられます テキストボックスに表示だと1件しか表示できませんね 条件が複数という点からも複数ヒットの可能性があります この程度のことならVBAを引っ張り出すまでもないですね 素直にクエリで表示でいいのではないですか 条件入力フォームにテキストボックスを3つ置き 入力後ボタンクリックで、クエリを開くなり クエリをソースとしたフォームを開いてやればいいですね(ここだけVBAかな) クエリでは 顧客IDの抽出条件欄に =[Forms]![フォーム名]![text顧客ID] 電話番号の抽出条件欄に =[Forms]![フォーム名]![text電話番号] 氏名の抽出条件欄に Like [Forms]![フォーム名]![text氏名] & "*" And [Forms]![フォーム名]![text氏名] Is Not Null 抽出条件はORになりますから行を変えて入力します 入力しなかった条件は無視されます

nana_poco
質問者

補足

ご指摘ありがとうございます。 このツールには先の話があり、表示させた項目を変更して DBにアップデートしたりコピー追加したりしたいので クエリでは対応できないのかなと思っていますがいかがでしょうか。

noname#22222
noname#22222
回答No.1

Q、ミスは? A、strRet = "顧客ID=" & Me!CustmID でバグはなくなるでしょう! ところで、少し、次のようなテーブルと検索フォームを作成してテストしてみました。 いずれにしろ、書くべきフォームのコードは10行以内です。 <顧客マスター> ID  氏名    住所 1   鈴木 一郎 東京 2   中村 主水 大阪 3   木村 太郎 京都 この場合の検索フォームのコードは、 Private Sub コマンド0_Click()   If Len(Me.ID & "") > 0 Then     Me.氏名 = DBLookup("氏名", "顧客マスター", "ID=" & Me.ID)     Me.住所 = DBLookup("住所", "顧客マスター", "ID=" & Me.ID)   End If End Sub 難点は、一々、レコードセットをオープンしていることです。 これを改善したのが、次です。 Private Sub コマンド1_Click()   Dim Datas() As String      If Len(Me.ID & "") > 0 Then     Datas() = DBSelects("氏名,住所", "顧客マスター", , "ID=" & Me.ID)     If Len(Datas(0, 0)) > 0 Then       Me.氏名 = Datas(0, 0)       Me.住所 = Datas(0, 1)     Else       Me.氏名 = ""       Me.住所 = ""     End If   End If End Sub Datas(レコードインデックス、フィールドインデックス) となっています。 DBSelects() は、該当するレコードの列情報を配列に読み込む関数です。 質問者の知りたい情報は、これらの関数が網羅していると思います。 Public Function DBLookup(ByVal strField As String, _              ByVal strTable As String, _              Optional ByVal strWhere As String = "", _              Optional ByVal ReturnValue = Null) As Variant On Error GoTo Err_DBLookup    Dim DataValue    Dim strQuerySQL As String    Dim rst     As ADODB.Recordset    Set rst = New ADODB.Recordset    strQuerySQL = "SELECT " & strField & " FROM " & strTable    If Len(strWhere) > 0 Then      strQuerySQL = strQuerySQL & " WHERE " & strWhere    End If    With rst      .Open strQuerySQL, _         CurrentProject.Connection, _         adOpenStatic, _         adLockReadOnly      If Not .BOF Then        .MoveFirst        DataValue = .Fields(0)      End If    End With Exit_DBLookup: On Error Resume Next    rst.Close    Set rst = Nothing    DBLookup = Nz(DataValue, ReturnValue)    Exit Function Err_DBLookup:    MsgBox "SELECT 文の実行時にエラーが発生しました。(DBLookup)" & Chr$(13) & Chr$(13) & _       "・Err.Description=" & Err.Description & Chr$(13) & _       "・SQL Text=" & strQuerySQL, _       vbExclamation, " 関数エラーメッセージ"    Resume Exit_DBLookup End Function Public Function DBSelects(ByVal strFields As String, _              ByVal strTable As String, _              Optional strGroupBy As String, _              Optional strWhere As String, _              Optional strOrderBy As String) As String() On Error GoTo Err_DBSelects   Dim I      As Integer   Dim J      As Integer   Dim R      As Integer  ' データを代入する配列 DataValue(,) のインデックスを決める行カウンター   Dim C      As Integer  ' データを代入する配列 DataValue(,) のインデックスを決める列カウンター   Dim M      As Integer  ' データを代入する配列 DataValue(,) の一つ目の添字の最大値=行総数 - 1   Dim N      As Integer  ' データを代入する配列 DataValue(,) の二つ目の添字の最大値=列総数 - 1   Dim strQuerySQL As String   Dim rst     As ADODB.Recordset   Dim fld     As ADODB.Field   Dim DataValues() As String      Set rst = New ADODB.Recordset      strQuerySQL = "SELECT " & strFields & " FROM " & strTable   If Len(strGroupBy) > 0 Then     strQuerySQL = strQuerySQL & " GROUP BY " & strGroupBy   End If   If Len(strWhere) > 0 Then     strQuerySQL = strQuerySQL & " WHERE " & strWhere   End If   If Len(strOrderBy) > 0 Then     strQuerySQL = strQuerySQL & " ORDER BY " & strOrderBy   End If   ' =================   ' Begin With: rst   ' -----------------   With rst      .Open strQuerySQL, _         CurrentProject.Connection, _         adOpenStatic, _         adLockReadOnly      If Not .BOF Then       ' --------------       ' 配列を再宣言       ' --------------       M = .RecordCount - 1       N = .Fields.Count - 1       If M > 99 Then         MsgBox "読込む行総数を100行に下方修正しました。(DBSelects)", vbInformation, " お知らせ"         M = 99       End If       ReDim DataValues(M, N)       ' ------------------------------------       ' 列情報を For-Next で配列に代入する       ' ------------------------------------       .MoveFirst       For R = 0 To M         C = -1         For Each fld In .Fields           C = C + 1           DataValues(R, C) = Nz(fld.Value, "")         Next fld         .MoveNext       Next R      Else       ReDim DataValues(0, 0)       DataValues(0, 0) = ""      End If   End With   ' ---------------   ' End With: rst   ' =============== Exit_DBSelects: On Error Resume Next   rst.Close   Set rst = Nothing   DBSelects = DataValues()   Exit Function Err_DBSelects:   M = 0   MsgBox "SELECT 文の実行時にエラーが発生しました。(DBSelects)" & Chr$(13) & Chr$(13) & _       "・Err.Description=" & Err.Description & Chr$(13) & _       "・SQL Text=" & strQuerySQL, _       vbExclamation, " 関数エラーメッセージ"   Resume Exit_DBSelects End Function

nana_poco
質問者

補足

ありがとうございます。 この場合、検索画面のIDをNullで電話番号のみで検索した場合ひっかからないとおもいます。それはここをいじればいいのかなとおもうのですが If Len(Me.ID & "") > 0 Then このチェックはどういう意味があるのでしょうか? また、ご指摘いただいたように結果が2レコード以上ある場合は 検索条件を絞り込むようメッセージをだしたいのですが、 可能でしょうか、よろしくお願いいたします。

関連するQ&A

  • コンパイルすると「メソッドまたはデータメンバが見つかりません」

    Access2000です。 名前を「Me!txt名前」に入力して「cmd探す」をクリックすると「メソッドまたはデータメンバが見つかりません」 「rs.FilterOn = True」でデバッグが中止します。 どなたかアドバイスお願いします。 ------------------------------ Private Sub cmd探す_Click() Dim cn As New ADODB.Connection Dim rs As New ADODB.Recordset   Dim strRet As String Set cn = CurrentProject.Connection rs.Open "Q_修正", cn, adOpenKeyset, adLockOptimistic strRet = "使用者氏名 Like'" & Me!txt名前 & "*'" rs.Filter = strRet rs.FilterOn = True ------------------------------

  • ACCESS SQLで複数データ表示させるには?

    *************************************************** Private Sub Form_Load() Dim cn As New ADODB.Connection Dim rs As New ADODB.Recordset Set cn = CurrentProject.Connection mySQL = "select * from テーブル" rs.Open mySQL, cn, adOpenForwardOnly, adLockOptimistic ’コントロールに代入 Me.No = rs![No] Me.項目 = rs![項目] ・・・ End Sub *************************************************** こんな感じで、クエリでなくSQLで フォームにテーブルの全レコードを表示させたい場合、 どのようにすればよいのでしょうか? 上の文には、何が不足しているのでしょうか? http://www.accessclub.jp/ado/09.html を見ましたが、解決できませんでした。

  • 【ACCESS2000】 VBAの更新処理に条件を加えたい。

    下記のような更新処理のVBAを組みました。 これにIDが5のものを更新するというのを加えるには どうすればよいでしょうか。 Dim cn As ADODB.Connection Dim rs As New ADODB.Recordset Set cn = CurrentProject.Connection rs.Open "tbl_D_売上", cn, adOpenKeyset, adLockOptimistic, adCmdTableDirect rs("入金方法") = 2 rs("入金方法名称") = "分割" rs.Update rs.Close Set rs = Nothing cn.Close Set cn = Nothing

  • ACCESS VBA

    ACCESSで検索フォームを作りたいと思っています。 VBAを使って行きたいと思うのですが、うまくいきません。 希望としては、該当するレコードのデータを抽出したいです。 よろしくお願いいたします。 ※現段階でのソースを書いてみました。 最終的に行いたい処理とは違うのですが、根本的に間違っているようなので簡略化しました。 /------------------------------------------------/ Private Sub コマンド1_Click() Dim cn As ADODB.Connection Dim rs As ADODB.Recordset Dim sql As String '接続 Set cn = CurrentProject.Connection 'レコードセットを取得 Set rs = New ADODB.Recordset sql = "SELECT * FROM 従業員データ " & _ "WHERE 年齢=30" rs.Open sql, cn, adOpenDynamic, adLockReadOnly rs.Close: Set rs = Nothing cn.Close: Set cn = Nothing End Sub /------------------------------------------------/

  • アクセスVBAの検索メソッドについてデバック

    前回もこちらで質問させていただいたことがある内容なのですが、引き続き、トラブルに悩まされています。仕組みがおかしくなっていたので、自分で触ってしまったことがまた悪影響だったのですが、、。 元々他の人が作ったものであり、いま、うまくいかない原因を探っているところです。まず、添付のシートにあるように、上の行のテーブルデータは"商品2_T"という名前のテーブル、下のデータは"商品2_T25discount"という名前のテーブルです。それぞれデータを引っ張ってきて、こちらのサイトに投稿するために貼り付けしました。 問題のコードをこちらに記載します。 Dim cn As ADODB.Connection Dim cn2 As ADODB.Connection Dim rs As ADODB.Recordset Dim rs2 As ADODB.Recordset Dim strmsg As String Dim lngRet As Long Dim strcriteria As String Set cn = CurrentProject.Connection Set rs = New ADODB.Recordset Set cn2 = CurrentProject.Connection Set rs2 = New ADODB.Recordset rs.Open "商品2_T", cn, adOpenKeyset, adLockOptimistic rs2.Open "商品2_T25discount", cn2, adOpenKeyset, adLockOptimistic MsgBox "更新を開始します  ", 64, 更新 Do Until rs.EOF '該当レコード摘出 If rs!MCD = Me!tx検索 Then '--------------------------------------------- strcriteria = "CAT = '" & rs!CAT & "'" ' --- A rs2.Find strcriteria, 0, adSearchForward If rs2.EOF Then ' Else rs!仕入単価 = rs2!discount End If '--------------------------------------------- rs!更新日 = Now() rs.Update End If rs.MoveNext Loop MsgBox "更新が完了しました  ", 64, 更新 (以上) やりたいことの説明ですが、まず、 If rs!MCD = Me!tx検索 Then とあるように、これはフォーム内にテキストボックスを用意していますので、ここに記入したMCDに一致するものに、検索をかける、ということです。そしてつぎに、strcriteria = "CAT = '" & rs!CAT & "'" 、(省略)rs!仕入単価 = rs2!discount とありますように、"CAT"を検索対象にし、前者のテーブルの"仕入単価"を、後者のテーブルの"discount"のデータで塗り替えます。 という私の解釈なのですが、(何せ他の人が作りましたので)正しいですよね? それで今試しているところなのですが、なぜかうまくいきません。何が間違っているのでしょうか? どういうエラーになるのかというと、これを実行すると、"更新日"というフィールドのみ、更新されて、仕入単価はそのままになります。ちなみに更新日が更新されているのは、このテキストボックスに入れたMCDが一致する全てのデータに対してですので、MCDが一致、には反応しているが、CATを検索して更新をかける、という動作に失敗しているように見えます。 しかし素人なのでこれ以上どうすればよいかがわかりません。どなたか少しでも解決策があれば教えていただけないでしょうか。

  • access ふたつのテーブル間でのデータ移動VB

    win10 office365 accessのテーブルの table1のフィールド IDの数値を table2のフィールド ID (いずれも長整数型 数値型 重複あり 空白の許容なし) にコピーする操作ですが 幾度か お尋ねしてきていますが 今回 このやり方で やってみました http://www.mahoutsukaino.com/ac/ac2002/vba/vba16/v16.htm 以下のコードにおいて rs2.Update ここの部分が黄色くなって とまってしまいます しかし なぜか 数値の移行は 出来ていました ただ止まってしまうと 次に続けられなく困っています Public Function table2table1() Dim cn As adodb.Connection Dim rs1 As adodb.Recordset Dim rs2 As adodb.Recordset Set cn = Application.CurrentProject.Connection Set rs1 = New adodb.Recordset Set rs2 = New adodb.Recordset rs1.Open "table1", cn, adOpenStatic, adLockReadOnly rs2.Open "table2", cn, adOpenKeyset, adLockOptimistic rs1.MoveFirst Do Until rs1.EOF rs2.Find "ID='" & rs1!ID & "'" If rs2.EOF Then rs2.AddNew rs2![ID] = rs1![ID] rs2.Update End If rs1.movenext Loop rs1.Close rs2.Close cn.Close End Function 以上 すみません 宜しくお願い致します

  • Accessのテーブルの文字列フィールドにVBAでアクセスするには?

    いつもお世話になっております。困っていることがありますので教えていただければ幸いです。 AccessのテーブルAに、メモ型のフィールドBがあり、1000文字くらいの文字が入っています。VBAの関数Cの中でそのテーブルにアクセスし、1000文字をいろいろ処理したいと思っています。見よう見まねで試しに Dim cn As ADODB.Connection Dim rs As ADODB.Recordset Dim FileNum As Integer Set cn = CurrentProject.Connection Set rs = New ADODB.Recordset rs.Open テーブルA, cn, adOpenDynamic, adLockOptimistic msgbox !フィールドB としてみたのですが、なぜか255文字までしか表示されません。VBAを用いてテーブル(やクエリ)にアクセスし、256文字以上の文字列を扱う方法はありませんでしょうか? 何かこちらで勘違いしているところがありましたら、ご指摘いただければと思います。よろしくお願いします。

  • ADO 「Set」は使ったほうがいいのでしょうか?

    Sub test1() Dim cn As ADODB.Connection Dim rs As ADODB.Recordset Set cn = New ADODB.Connection Set rs = New ADODB.Recordse End Sub Sub test2() Dim cn As New ADODB.Connection Dim rs As New ADODB.Recordset End Sub この二つは同じ意味ですか? 「Set」は使ったほうがいいのでしょうか? よろしくお願いします。

  • レコードは2行あるのに「-1」が返ってくる

    accessです。 テーブル1にレコードは2行あるのに、下記のコードを実行すると「-1」が返ってきます。 なぜでしょうか? ------------------------------------------------------------ Sub test() Dim cn As ADODB.Connection Dim rs As ADODB.Recordset Set cn = Application.CurrentProject.Connection Set rs = cn.Execute("SELECT * FROM テーブル1") MsgBox rs.RecordCount rs.Close cn.Close Set rs = Nothing Set cn = Nothing End Sub ------------------------------------------------------------ ご教示よろしくお願い致します。

  • CMD.Executeの結果をメッセージボックスで表示したい

    Public Sub SQLActionCmd()     Dim CN As ADODB.Connection     Dim CMD As ADODB.Command     Dim MYSQL As String     '接続     Set CN = CurrentProject.Connection     '更新     MYSQL = "SELECT * FROM 名簿 WEHRE 性別 = "男" ;"     Set CMD = New ADODB.Command     CMD.ActiveConnection = CN     CMD.CommandText = MYSQL     CMD.Execute    '終了     Set CMD = Nothing     RS.Close: Set RS = Nothing     CN.Close: Set CN = Nothing    End Sub と言う感じで実際にはAccessのフォームのボタンをクリックしたタイミングでコードをかいているのですが、このCMD.EXECUTEを実行した結果、テーブルに該当データがなければない旨のメッセージボックスを出したいのです。 そういうことは可能でしょうか?