同じ列を持つ2つのテーブルをExcelでマージするにはどうすればよいですか?


11

Excelには、SQLデータベースからテーブルにデータをプルし、そのデータに基づいてレポートを生成するスプレッドシートがあります。残念ながら、このSQLデータベースのデータは不完全なため、スプレッドシートに手動で入力した結果セットに行を追加したいと考えています。

ExcelがSQLデータベースから新しいデータをプルするたびに削除されるため、これらの追加の行を手動でテーブルに挿入することはできません。そのため、代わりに、新しいシートに同じ列見出しを持つ別のテーブルを作成してそこにデータを入力し、別のシートに3番目のテーブルを作成して、SQLとデータを手動で入力するテーブル。どうすればこれを達成できますか?(または代わりに、これを行うより良い方法はありますか?


例:

Table 1 (From Database):

  | Person | Week Of | Task | Hours |
  | Bob    | 1/6/13  | Foo  | 12    |
  | Mary   | 1/6/13  | Foo  | 7     |
  | Mary   | 1/6/13  | Bar  | 5     |
  | John   | 1/6/13  | Foo  | 5     |
  | John   | 1/13/13 | Foo  | 13    |

-

Table 2 (Entered Manually): 
  | Person | Week Of | Task | Hours |
  | Bob    | 1/6/13  | Baz  | 3     |
  | Mary   | 1/6/13  | Baz  | 2     |
  | John   | 1/13/13 | Baz  | 5     |

-

Result:
  | Person | Week Of | Task | Hours |
  | Bob    | 1/6/13  | Foo  | 12    |
  | Mary   | 1/6/13  | Foo  | 7     |
  | Mary   | 1/6/13  | Bar  | 5     |
  | John   | 1/6/13  | Foo  | 5     |
  | John   | 1/13/13 | Foo  | 13    |
  | Bob    | 1/6/13  | Baz  | 3     |
  | Mary   | 1/6/13  | Baz  | 2     |
  | John   | 1/13/13 | Baz  | 5     |

手動で追加したデータがSQLデータの下にある場合は問題ありませんか?または、日付順に並べ替える必要がありますか。Excelは、既存のSQLデータ行のすぐ下にある行を上書きしません。しかし、両方のデータ型をソートする必要がある場合は、全体がさらに複雑になります。
nixda 2013年

まあ、私はそれらを並べ替えることを好みますが、それは完全に必要なわけではありません。重要なことは、ピボットテーブルや他のExcelツールを使用して、データセット全体(手動で入力されたテーブルと自動的に入力されたテーブルの両方を含む)を分析できることです。また、SQLから新しいデータを自動的にプルし続けられるようにする必要もあります。
Ajedi32 2013年

この動作は解決策でしょうか?後最初のクエリと後の2番目のクエリ。そしてもちろん、Excelはワークブックを開いたときにSQLを自動更新します。
nixda 2013年

それはうまくいくと思います。フィルターや並べ替えなどができるように、データを単一のテーブルに入れたいのですが、前に言ったように、それは必ずしも必要ではありません。
Ajedi32 2013年

多分私達はあなたの分類問題の解決策を見つけます。ただし、最初のステップとして、新しいワークブックで初めてSQLをクエリします。その後、そのすぐ下に手動エントリを追加します。次に、2番目(およびそれ以降)のクエリでテストします。それらは上書きされません。その標準的な動作。特別なことはありません。
nixda 2013年

回答:


2

VBAを使用しない純粋なExcelソリューションを次に示します。これは、INDEX関数を使用して、SQLデータの行および列全体をステップダウンし、値がすべて使用されてエラー条件が発生するまで機能します。IFERROR関数はエラーをキャッチし、2番目のINDEX関数を使用して、手動で入力されたデータの行および列全体をステップダウンし、これらの値がすべて使用されてエラー条件が発生するまで繰り返します。2番目のIFERROR関数はエラーをキャッチし、ダッシュ( "-")を返します。(式が正しい結果を生成するには、リボンを介してSQLデータを更新する必要があります。)

の式を使用して、Sheet1のSQLデータの動的名前付き範囲SQLDBを作成します

=OFFSET(Sheet1!$A$2,0,0,COUNTA(Sheet1!$A:$A)-1,COUNTA(Sheet1!$1:$1))

作成式を使用してシート2に手動で入力されたデータのための範囲EXCELRNG名前第2のダイナミックました:

=OFFSET(Sheet2!$A$1,1,0,COUNTA(Sheet2!$A:$A)-1,COUNTA(Sheet2!$1:$1))

これらの名前付き範囲はどちらも、変数名が2つのシートのそれぞれの行1に入力されていることを前提としています。

Sheet3の行1(セルA1で始まる)に変数名を入力します。

Sheet3のセルA2に次の数式を入力します。

=IFERROR(INDEX(SQLDB,ROWS(A$2:A2),COLUMN(A2)),IFERROR(INDEX(EXCELRNG,ROWS(A$2:A2)-ROWS(SQLDB),COLUMN(A2)),"-"))

変数名の列に数式をコピーし、数式の結果がすべてダッシュ( "-")になるまで行を下にコピーします。

次のステップとして、分析と整理のために別のシートにピボットテーブルを作成することができます。

再び最初のステップは、動的な名前付き範囲、たとえばRESULTRNGを作成し、名前付き範囲のName Manager入力ボックスに次の数式を挿入することです。

=OFFSET(Sheet3!$A$1,0,0,COUNTA(Sheet1!$A:$A)+COUNTA(Sheet2!$A:$A)-1,COUNTA(Sheet1!$1:$1))

次に、新しいシートにピボットテーブルを作成し、分析するテーブルとしてRESULTRNGを設定します。これにより、シート3の数式テーブルから末尾のダッシュがすべて除外されます。

これは、RESULTRNG式がSheet1とSheet2の行の総数(Sheet2のヘッダーを除く)とSheet1の列の総数をカウントし、それらの数に基づいて範囲を設定し、後続の行のダッシュを除いて(または列)をSheet3の数式テーブルで使用します。


このようにした場合、結合されたテーブルは固定サイズである必要はありませんか?また、テーブルを必要以上に大きくした場合、結合されたテーブルのデータを処理するピボットテーブルを作成しようとすると、失敗しませんか?(表の値の一部が「-」文字になるためですか?)または、これらの問題を回避する方法はありますか?
Ajedi32 2013年

(ところで、私は一般に、このような純粋なExcelソリューションを好みます。ユーザーがマクロを有効にする前にマクロを有効にする必要がないためです。)
Ajedi32

式が2つのテーブルのすべてのデータを確実にキャプチャするようにするには、手作業による保守が必要になります。ダッシュを回避するには、数式をダッシュ​​ではなく、データを返した場所にのみコピーする必要があります。
2013年

マージされたテーブルから空白ではない(「-」文字で埋められた)行のみを含む別の名前付き範囲を作成することはできますか?そうすれば、ピボットテーブルを設定してその範囲からデータを取得でき、ダッシュを気にする必要がなくなります。
Ajedi32 2013年

ダッシュを除いてピボットテーブルを作成する方法を説明するために、回答を拡張しました。「ダッシュなし」のテーブルを配置しようとすると、ソースデータの行数が変更されるたびに新しいテーブルのサイズが手動で変更されない限り、ダッシュの問題は別のシートに転送され、#N / Aがダッシュセルに表示されます。
2013年

5

私はそれをする方法を見つけました。このソリューションは少しトリッキーであり、両方のテーブルに独自の個別のシート(他には何もない)が必要ですが、それ以外はほぼ正確に私が望んでいることを行います。(また、結合などのより複雑な操作を行う可能性がたくさんあるようです。)

リボンの[データ]タブに移動し、[他のソースから]と[Microsoft Queryから]をクリックします。次に、[Excelファイル]をクリックし、現在作業中のファイルを選択して[OK]をクリックします。次に、[キャンセル]をクリックし、Microsoft Queryで編集を続行するかどうかを尋ねられたら、[はい]をクリックします。ここから[SQL]ボタンをクリックして、スプレッドシートの任意のシートにカスタムSQLクエリを書き込むことができます。私の場合:

SELECT *
FROM `'Sheet1$'` `'Sheet1$'`
UNION ALL
SELECT *
FROM `'Sheet2$'` `'Sheet2$'`

注:私にとって、このメソッドは、ファイルを閉じて再度開いた後に機能しなくなります。とにかくそれをここに投稿しますが、それは私のコンピューターの問題だけの場合、または他の誰かがそれを機能させることができる場合に備えています。


1
2つの異なるワークブックを接続して正常に動作します。それがまさに私が必要としていたことです。ありがとうございました!
daVe 2015年

この方法は私にはとてもうまくいきます。クエリを実行し、データと過去を単にExcelにコピーします。ただし、データから重複行が削除されることに注意してください。この回答を少し編集してもかまいません。
Some_Guy 2016

これは実際に私に起こったので追加し、ピボットテーブルを作成していくつかの合計を取得する前に、これを使用して一連の販売データを1つのスプレッドシートにマージしました。逃した。
Some_Guy

@Some_Guy代わりにUNION ALLを使用してください。
Ajedi32 2016

3

VBAソリューションに興味がある場合は、以下を機能させることができました。

  • SQL Serverから取得するデータの動的な名前付き範囲を設定します。Name Managerを開き、新しい名前(たとえば、「SQLDB」)を入力し、[参照先]入力ボックスに次の式をコピーします。プルインされたデータはSheet1にあると想定しています。

    =OFFSET(Sheet1!$A$1,0,0,COUNTA(Sheet1!$A:$A),COUNTA(Sheet1!$1:$1))
    
  • 手動データが入力される範囲に別の名前付き範囲を設定します。EXCELRNGという名前を使用し、Sheet2にあると想定しました。名前付き範囲は、ヘッダー行を除外するために行2から始まります。ここでの式は、参照するシートを除いて最初の式と同じです。

    =OFFSET(Sheet2!$A$1,1,0,COUNTA(Sheet2!$A:$A)-1,COUNTA(Sheet2!$1:$1))
    
  • 以下は、SQLテーブルへの接続に使用した最初の設定セットです。ダイアログボックスにアクセスするには、リボンの[データ]タブで[接続]を選択します。バックグラウンド更新を無効にすると、Excelシートのデータの更新が完了するまでVBAマクロが一時停止します。ワークシートを開いたときに接続を更新する必要はないかもしれませんが、マクロが実行される前に認証が行われるようにしたかったのです。

接続設定

  • 以下は、2番目の設定セットです。これらは、[データ]タブの[プロパティ]セクションにあります(インポートされたSQLテーブルのセルが選択されている間)。「新しいデータの行全体を挿入し、未使用のセルを削除する」オプションを選択しましたが、「セルを挿入...」オプションで問題が発生することはありませんでした。

接続プロパティ

  • 最後に、これはVBAコードです。挿入するには、[開発]タブの[Visual Basic]を選択します。左側のリストでワークシート名を強調表示します。これは「VBAプロジェクト(シート名)として参照されます。次に、画面上部のメニューバーで[モジュールの挿入]を選択し、コードを新しいモジュールに貼り付けます。統合テーブルをSheet3に配置していることに注意してください。マクロは新しいテーブルを並べ替えませんが、追加するのは難しくありません。

    Sub StackTables()
    
       Dim Rng1 As Range, Rng2 As Range
    
       Set Rng1 = ThisWorkbook.Names("SQLDB").RefersToRange
       Set Rng2 = ThisWorkbook.Names("EXCELRNG").RefersToRange
    
       ' refresh the SQL table
       ThisWorkbook.Connections(1).Refresh
    
       ' clear the consolidated table range  
       Sheet3.Cells.ClearContents
    
       ' copy the SQL data into the consolidation range
       Rng1.Copy
       Sheet3.Range("A1").PasteSpecial xlPasteValues
    
       'copy the manually entered data into the consolidate range
       Rng2.Copy
       Sheet3.Range("A1").Offset(Rng1.Rows.Count, 0).PasteSpecial xlPasteValues
       Application.CutCopyMode = False
    
       Sheets("Sheet3").Activate
       ActiveSheet.Range("A1").Select
    
    End Sub
    

これはかなり固い解決策のように見えます。でもいくつか質問があります。このマクロをトリガーするものは何ですか?データ接続を更新すると自動的に実行されますか、それとも手動で実行するために別のボタンを押す必要がありますか?次に、これはテーブルで機能しますか?(テーブルとしてフォーマットされていない範囲だけではありません)その場合、テーブル自体は並べ替えを処理できませんか?(VBAマクロがソートを実行する代わりに、あなたが提案したように?)
Ajedi32

1
現状では、[開発]タブから[マクロ]を選択し、マクロを選択して実行することで、マクロを実行します。2つの選択肢:リボンのカスタムボタンに割り当て、それを使用して実行します。または、Worksheet_Activateイベントにマクロコードとして埋め込みます。これは、統合シートを選択するたびに実行されます。並べ替えが可能なテーブルで動作します。ただし、データが追加されたときにテーブルが自動的に再ソートされるかどうかはわかりません。
チャフ

3

これは、@ chuffの「Pure Excel」ソリューションバージョンで、テーブルを操作するように特別に設計されています。(IEマージする2つのデータソースはテーブルです。)

この方法と彼の回答に投稿された1つのチャフとの主な違いは、マージする2つのデータセットはテーブルであり、すでに独自の名前付き範囲があるため、名前付き範囲を定義する必要がないことです。したがって、最初のテーブルTable1に名前を付け、2番目のテーブルに名前を付けますTable2

次に、新しいシートの左上隅に新しいテーブルを作成し、他の2つのテーブルと同じ列名を付けます。次に、作成したシートのセルA2に次の数式を入力します。

=IFERROR(INDEX(Table1,ROWS(A$2:A2),COLUMN(A2)), IFERROR(INDEX(Table2,ROWS(A$2:A2)-ROWS(Table1),COLUMN(A2)), "-"))

次に、すべてのテーブル列にこの数式をコピーし、数式の結果がすべてダッシュ( "-")になるまで行を下にコピーします。注:各セルの内容は実際には同じであるため(これらはすべて同じ数式を含んでいるため)、この新しいテーブルを並べ替えても何も起こりません。

マージされたテーブルの列に空白のセルが表示されるはずのときに0が表示される場合は、次のように、その列の数式を代替関数でラップできます。

=SUBSTITUTE(<old expression here>, 0, "")

この新しいテーブルのデータを使用するピボットテーブルを作成する場合は、名前付き範囲を作成する必要があります。まず、テーブルに名前を付けますTable3。次に、数式タブに移動し、[名前の定義]をクリックします。参照に名前を付け、その値に次の方程式を入力します(「参照先」):

=OFFSET(Table3[#All],0,0,ROWS(Table1)+ROWS(Table2)+1)

その後、この名前付き参照をピボットテーブルの範囲として使用できます。


0

1回限りの結果が必要な場合は、2つのテーブルをマージするWebサイトがあります。https//office-tools.online/table/merge/

テーブルをWebページに貼り付け、関連するパラメーターを選択します。以下は、組み込みの例のスクリーンショットで、使用方法を示しています。

ここに画像の説明を入力してください

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.