私は仕事で過度に複雑で不十分に設計されたソフトウェアを使用していますが、今、ある期間に発行された請求書のレポートを作成する必要があります。
請求書はテーブルENTR2012で保持され、次の構造を使用します。
CREATE TABLE ENTR2012 (
ABREV VARCHAR(8) NOT NULL,
NOTA VARCHAR(9) NOT NULL,
NUMEROEMIT VARCHAR(18) NOT NULL,
DATAENTRADA TIMESTAMP,
DATAEMISSAO TIMESTAMP,
VALCONTABIL DOUBLE PRECISION,
PRIMARY KEY (ABREV,NOTA,NUMEROEMIT)
この表では、ABREV、NOTA、NUMEROEMIT、DATAENTRADA、DATAEMISSAO、VALCONTABILのみが必要です。
これは私のテーブルでなければなりません:
| ABREV | NOTA | NUMEROEMIT | DATAENTRADA | DATAEMISSAO | VALCONTABIL |
| dep1 | 001 | 1234567 | 01.01.2012 | 31.01.2012 | 1,000.00 |
| dep2 | 001 | 898909201 | 02.01.2012 | 16.01.2012 | 998.00 |
ご覧のように、ABREVは請求書を発行した部門IDを保持し、NOTAは請求書の番号(および各出発には独自の請求書カウントがあります)、NUMEROEMITはクライアントID、DATAENTRADAは請求書が発行された日付、DATAEMISSA請求書が支払われた日であり、VALCONTABILは請求書の値です。
次に、請求書の説明、つまり正確に請求するものを見つける必要があります。
2番目の表、ITST2012は説明を保持します。
CREATE TABLE ITST2012 (
ABREV VARCHAR(8) NOT NULL,
NOTA VARCHAR(9) NOT NULL,
NUMEROEMIT VARCHAR(18) NOT NULL,
DATAENTRADA TIMESTAMP,
CODPRODUTO VARCHAR(13),
ALIQISS DOUBLE PRECISION,
VALTOTAL DOUBLE PRECISION,
PRIMARY KEY (ABREV,NOTA,NUMEROEMIT)
ITSTには、ABREV(部門ID)、NOTA(請求書番号)、DATAEMISSAO(発行日)、およびCODPRODUTO(製品コード)とALIQISS(上司がこのレポートに必要な便利な番号)が必要な情報があります。
各部門(ABREV)には独自の番号付け順序(NOTA)があるため、depを比較する必要があります。 ID(ABREV)、番号(NOTA)、および値(VALTOTAL)を同時に確認して、これが正しい請求書であることを確認します。製品は次のようになります。
| ABREV | NOTA | NUMEROEMIT | DATAENTRADA | DATAEMISSAO | VALCONTABIL | ITST2012.CODPRODUTO | ITST2012.ALIQISS |
| dep1 | 001 | 1234567 | 01.01.2012 | 31.01.2012 | 1,000.00 | 2 | 5.00 |
| dep2 | 001 | 898909201 | 02.01.2012 | 16.01.2012 | 998.00 | 3 | 15.00 |
次に、実際の製品の説明をITST2012.CODPRODUTOに結合する必要があります。繰り返しになりますが、各部門は独自の記数法を使用しているため、ABREV(dep。ID)とCODPRODUTO(製品ID)をテーブルPRODUTOSと一致させる必要があります。
CREATE TABLE PRODUTOS (
ABREV VARCHAR(8) NOT NULL,
CODIGO VARCHAR(13) NOT NULL,
DESCRICAO VARCHAR(50),
PRIMARY KEY (ABREV,CODIGO)
ABREV = PRODUTOS.ABREVおよびITST2012.CODPRODUTO = PRODUTOS.CODIGOであることを確認する必要があるだけです。テーブルは次のようになります。
| ABREV | NOTA | NUMEROEMIT | DATAENTRADA | DATAEMISSAO | VALCONTABIL | ITST2012.CODPRODUTO | PRODUTOS.DESCRICAO | ITST2012.ALIQISS |
| dep1 | 001 | 1234567 | 01.01.2012 | 31.01.2012 | 1,000.00 | 2 | my_product | 5.00 |
| dep2 | 001 | 898909201 | 02.01.2012 | 16.01.2012 | 998.00 | 3 | my_product2 | 15.00 |
最後に、クライアントID(最初のテーブルのNUMEROEMIT)を、すべてのクライアントを保持するテーブルFORNECと結合する必要があります(今回は、部門をチェックする必要がなく、すべてに同じテーブルを使用します)。
CREATE TABLE FORNEC (
RAZSOC VARCHAR(55),
CNPJCPF VARCHAR(18),
NUMEROEMIT = FORNEC.CNPJCPFに一致させ、RAZSOC情報を取得するだけです。
レポートの最終的な表は次のとおりです。
| ABREV | NOTA | NUMEROEMIT | FORNEC.RAZSOC | DATAENTRADA | DATAEMISSAO | VALCONTABIL | ITST2012.CODPRODUTO | PRODUTOS.DESCRICAO | ITST2012.ALIQISS |
| dep1 | 001 | 1234567 | my_client | 01.01.2012 | 31.01.2012 | 1,000.00 | 2 | my_product | 5.00 |
| dep2 | 001 | 898909201 | my_client2 | 02.01.2012 | 16.01.2012 | 998.00 | 3 | my_product2 | 15.00 |
私の問題は次のとおりです。 SQLを使用して、これらすべてのテーブルを同時に結合する方法はわかりません。クライアントを簡単に結合できますが、同時に多くのフィールドを比較し、正しい方法で結合するクエリを作成できません。自分のデザインのデータベースでのみ作業を行ったので、私はかなり絶望的です。このマカロニデータベースでは、情報が多すぎてテーブルが少なすぎます。
私と一緒にこれをつなぐことができるSQL Wizardに感謝します。
PS。データベースは行IDのないFirebirdです。
質問にお答えしましたので、よろしくお願いします!
最終的なコードは次のとおりです。
SELECT notas.ABREV, notas.NOTA, notas.NUMEROEMIT, prestador.RAZSOC, notas.DATAENTRADA, notas.DATAEMISSAO, notas.VALCONTABIL, itens.CODPRODUTO, prod.DESCRICAO, itens.ALIQISS FROM ENTR2012 notas
INNER JOIN ITST2012 itens
ON notas.ABREV=itens.ABREV AND notas.NOTA=itens.NOTA AND notas.VALCONTABIL=itens.VALTOTAL
INNER JOIN PRODUTOS prod
ON itens.ABREV=prod.ABREV AND itens.CODPRODUTO=prod.CODIGO
INNER JOIN FORNEC prestador
ON itens.NUMEROEMIT=prestador.NUMERO;
これがあなたのこのデータベースで機能するかどうかは本当にわかりませんが、Oracle XEデータベースではるかに単純な値とテーブルを使用してテストを行ったところ、問題なく動作しました。
SELECT * FROM ENTR2012
INNER JOIN ITST2012
ON ENTR2012.ABREV=ITST2012.ABREV AND ENTR2012.NOTA=ITST2012.NOTA AND ENTR2012.VALTOTAL=ITST2012.VALTOTAL
INNER JOIN PRODUTOS
ON ITST2012.ABREV=PRODUTOS.ABREV AND ITST2012.CODPRODUTO=PRODUTOS.CODIGO
INNER JOIN FORNEC
ON ITST2012.NUMEROEMIT=FORNEC.CNPJCPF;
執筆中に道に迷ったかもしれないので、値や列などを見直してください。