1

Microsoft Accessで、同じキー(=重複している)を持つテーブルの特定の列を新しいテーブルにマージしたいと思います。

ソーステーブルは次のようになります

Key Content
Apple   X
Banana  B
Banana  D
Banana  E
Banana  G
Lemon   A
Lemon   X
Orange  A

キーごとにエントリが1つだけで、各キーに対応するすべての「コンテンツ」フィールドが1つのフィールドに蓄積されたフィールドを持つ新しいテーブルを作成したいと思います。各「コンテンツ」値は、次のように区切る必要があります。

Apple   X
Banana  B<x>D<x>E<x>G
Lemon   A<x>X
Orange  A

上記のようにしたいと思いますが、以下のように異なるフィールド/列にある場合にも機能する可能性があります。

Apple   X
Banana  B   D   E   G
Lemon   A   X
Orange  A

私はこれで本当に助けていただければ幸いです。これをグーグルで検索すると、サードパーティのアドオン(このようなものhttp://www.tucows.com/preview/1586663/MS-Access-Join-Two-Tables-Software)がいくつかあることがわかりました。これを解決することですが、確かにこれはMSAccess自体で実行できます…。または…?

4

2 に答える 2

1

1 つのバージョンは、UDF と次のクエリを使用することです。

SELECT Distinct Fruit.Key, 
    ConcatADO("SELECT Content FROM Fruit WHERE Key='" & [Key] & "'","<x>","<x>") 
       AS AllRows 
INTO NewFruit
FROM Fruit

ユーザー定義関数 (UDF)

Function ConcatADO(strSQL As String, strColDelim, strRowDelim)
   Dim rs As New ADODB.Recordset
   Dim strList As String

   On Error GoTo Proc_Err

       If strSQL <> "" Then
           rs.Open strSQL, CurrentProject.Connection
           strList = rs.GetString(, , strColDelim, strRowDelim)
           strList = Mid(strList, 1, Len(strList) - Len(strRowDelim))
       End If

       ConcatADO = strList

   Exit Function

Proc_Err:
       ConcatADO = "***" & UCase(Err.Description)
End Function

クエリ デザイン ウィンドウ内で作業すると、クロス集計を作成できます。

TRANSFORM Min(Fruit.Content) AS MinOfContent
SELECT Fruit.Key
FROM Fruit
GROUP BY Fruit.Key
PIVOT Fruit.Content;

どちらが返されますか

Key     A   B   D   E   G   X
Apple                       X
Banana      B   D   E   G   
Lemon   A                   X
Orange  A

その後、クロス集計を保存し、クロス集計に基づいて新しいクエリを作成できます。このクエリは、新しいテーブルを取得するテーブルの作成クエリである可能性がありますが、ご覧のとおり、いくつかの列があります。

キーごとにあらかじめ決められた数の可能な行がある場合は、他のアプローチがあります。

最後に、非正規化は本当に進むべき道なのか、自問する必要があります。

于 2013-01-31T12:10:54.913 に答える
1

もう 1 つの方法は、2 つの列 (キー、コンテンツ) を持つテーブルを作成し、以下の関数を実行してデータを新しいテーブルにコピーすることです。「ExistingTableName」と「NewTableName」をテーブル名に置き換える必要があります。

Sub CreateNewTable()
    Dim rs As Recordset
    Dim rsContent As Recordset
    Dim strContent As String
    'Select and loop through all keys
    Set rs = CurrentDb.OpenRecordset("SELECT DISTINCT Key FROM [ExistingTableName]")
    Do Until rs.EOF
      'Select all content records for this key and combine into a string
      Set rsContent = CurrentDb.OpenRecordset("SELECT Content FROM [ExistingTableName] WHERE Key = " & Chr(34) & Nz(rs!Key) & Chr(34))
      strContent = ""
      Do Until rsContent.EOF
        strContent = strContent & rsContent!Content & ","
        rsContent.MoveNext
      Loop
      If Len(strContent) > 0 Then
      strContent = Mid(strContent, 1, Len(strContent) - 1)
      End If
      CurrentDb.Execute "INSERT INTO [NewTableName] (Key, Content) VALUES (" & Chr(34) & Nz(rs!Key) & Chr(34) & ", " & Chr(34) & Nz(strContent) & Chr(34) & ")"
      rs.MoveNext
    Loop

    Set rs = Nothing
    Set rsContent = Nothing
End Sub

VBAなしでこれを行う方法はないと思います。

リレーショナル データベースを使用しているため、1 つのテーブルを使用してキーを格納し、別のテーブルを使用してコンテンツを格納することを検討する必要があります (行/レコードごとに 1 つのコンテンツ)。次に、3 番目のテーブルを使用するか、「キー」をコンテンツ テーブルの外部キー。また、すべての MS Access テーブルで常に自動番号を主キーとして使用します。他のすべての理由でこれが良い考えであるとは限りませんが、単に破損を回避し、'aple' などのスペルミスを 'apple' に変換せずに変更できるようにするためです。あなたの関係を壊します。

于 2013-01-31T14:28:52.257 に答える