Join com 3 tabelas

14/02/2006

Olá amigos,
Estou querendo fazer uma JOIN com 3 tabelas, há como fazer isso, pois no meu relatório tenho que colocar o NOME em Extenso e também o mês, que estão em tabelas diferente.

Tem como fazer algo melhorado?

select * from DIZIMO D JOIN PESSOAS P JOIN MESESEXTENSOS M on D.NOMEDIZIMISTA = P.CODIGOPESSOA and D.MES = M.MESEXTENSO

Isso naum deu certo. Porque?

Obrigado,
Rodrigo


Rodrigorpb

Respostas

14/02/2006

Titanius

Amigo, coloque a DDL das tabelas em questao, assim poderemos ver para ajuda-lo

[]s


Responder Citar

14/02/2006

Rodrigorpb

TAbela Dizimo que tem o Mês em Integer e Nome do Dizimista em Integer tb, quero colocá-las em extenso.

/* Table: DIZIMO */

CREATE TABLE DIZIMO (
    CODIGO INTEGER NOT NULL,
    NOMEDIZIMISTA INTEGER NOT NULL,
    ANO INTEGER,
    MES INTEGER,
    VALOR NUMERIC(12,2),
    DATAOFERTA DATE);



/* Primary keys definition */

ALTER TABLE DIZIMO ADD  PRIMARY KEY (CODIGO);



Tabela Pessoal que tem o nome do Dizimista em Extenso.

/* Table: PESSOAS */

CREATE TABLE PESSOAS (
    CODIGOPESSOA INTEGER NOT NULL,
    NOMEPESSOA VARCHAR(60) NOT NULL,
    DATANASCIMENTO DATE,
    CASADORELIGIOSO CAMPO5,
    NOMECONJUGE VARCHAR(60),
    DATACASAMENTO DATE,
    NATURALDE VARCHAR(40),
    UFNATURAL CHAR(2),
    NACIONALIDADE VARCHAR(40),
    SEXO INTEGER,
    ESTADOCIVILPES INTEGER,
    PROFISSAO INTEGER,
    EMAIL VARCHAR(40),
    ENDERECO VARCHAR(60),
    NUMERO INTEGER,
    COMPLEMENTO VARCHAR(20),
    BAIRRO VARCHAR(40),
    CIDADE INTEGER,
    UF CHAR(2),
    CEP VARCHAR(10),
    TELEFONE1 VARCHAR(14),
    TELEFONE2 VARCHAR(14),
    CELULAR VARCHAR(14),
    FAX VARCHAR(14),
    PAI VARCHAR(60),
    MAE VARCHAR(60),
    BATIZADO CAMPO5,
    DATABATISMO DATE,
    EUCARISTIA CAMPO5,
    CRISMADO CAMPO5,
    CATEQUISTA VARCHAR(15),
    COMUNIDADEPES INTEGER,
    GRUPOPES INTEGER,
    MINISTERIOPES INTEGER,
    MOVIMENTOPES INTEGER,
    PASTORALPES INTEGER,
    DIZIMISTA CAMPO5,
    OBS BLOB sub_type 1 segment size 80);



/* Primary keys definition */

ALTER TABLE PESSOAS ADD  PRIMARY KEY (CODIGOPESSOA);



Tabela Mes, também criei para colocar o mês em Extenso, pq estou usando no Relatório Report Builder 7.

/* Table: MESESEXTENSOS */

CREATE TABLE MESESEXTENSOS (
    CODIGOMES INTEGER NOT NULL,
    MESNUMERICO INTEGER NOT NULL,
    MESEXTENSO VARCHAR(10) NOT NULL);



/* Primary keys definition */

ALTER TABLE MESESEXTENSOS ADD  PRIMARY KEY (CODIGOMES);



Responder Citar

15/02/2006

Titanius

Olá amigo, tente assim:

select d.*, m.mesextenso from dizimo d
left join pessoas p on (p.codigopessoa = d.nomedizimista)
left join MESESEXTENSOS m on (m.mesnumerico = d.mes)


Lembre-se que para funcionar legal você deve criar uma FK no Campo NOMEDIZIMISTA vinculado à tabela PESSOAS, e no campo MES vinculado ao campo MESNUMERICO da tabela MESEXTENSOS.

Se não colcoar funciona, mas seria legal por... ok?

Qualquer coisa fal aí.


Responder Citar

15/02/2006

Rodrigorpb

Muito obrigado, funciona certinho.


[b:12b93eab46]OUTRA PERGUNTA[/b:12b93eab46]


Aproveitando o post, gostaria de tirar uma dúvida em relação aos comandos que uso para Gravar, Cancelar. Não estou usando nesta aplicação Store Procedure no DB, estou usando o IBX, FB 1.5, delphi7.


Botão Gravar

Procedure TFPessoas.BtnGravarClick(Sender: TObject);
Begin
  Try
    Screen.Cursor := crSQLWait;
    If (edNomePessoa.Text = ´´) or (edDataNasc.EditText = ´  /  /    ´) or (DBLookupComboBox1.Text = ´´)
    or (edEstadoCivil.Text = ´´) or (edCidade.Text = ´´) Then
      begin
           ShowMessage(´O(s) campo(s) está(ão) em branco! Verefique os campos:´ + #13 +
           ´Nome / Data de Nascimento / Sexo / Estado Civil / Cidade´);
           ednomepessoa.setfocus;
           abort;
     end
    Else
    If Not(Transaction.InTransaction) Then
      Transaction.StartTransaction;
      Query.Post;
      Query.ApplyUpdates;
      Transaction.CommitRetaining;
      MessageDlg(´O(A) Participante [ ´+DM.qPessoasNOMEPESSOA.Value +´ &93; foi Salvo(a) com Sucesso !´, mtWarning, &91;mbOK&93;, 0);
      HabilitarBotoes;
   Finally
    Screen.Cursor := crDefault;
    If (edNomePessoa.Text <> ´´) and (edDataNasc.EditText <> ´  /  /    ´) and (DBLookupComboBox1.Text <> ´´)
    and (edEstadoCivil.Text <> ´´) and (edCidade.Text <> ´´) Then
      begin
        BtnIncluir.SetFocus;
      end;
  End;
End;




Botão Cancelar

 If not DM.TSSACRATUS.InTransaction then
 DM.TSSACRATUS.StartTransaction;
 DM.qPessoas.Cancel;
 DM.TSSACRATUS.RollbackRetaining;
 HabilitarBotoes;




Obrigado novamente.


Responder Citar

15/02/2006

Titanius

Amigo, e qual seria a sua dúvida?


[]s


Responder Citar

15/02/2006

Rodrigorpb

OPSS... descumpe-me,

:D


Está correto estes códigos para gravar e cancelar, ou teria algo melhor, mas seguro?


Rodrigo


Responder Citar

15/02/2006

Michael

Olá!

Dicas:

[b:979322c832]1)[/b:979322c832] Para validar a entrada do usuário, faça a verificação diretamente nos fields do [b:979322c832]DataSet[/b:979322c832], ao invés dos controles de edição. Desta forma vc pode tratar valores [b:979322c832]NULL [/b:979322c832]e [b:979322c832]default[/b:979322c832], o que é mais seguro do que comparar strings;

[b:979322c832]2)[/b:979322c832] Parece que vc está usando [b:979322c832]dbExpress [/b:979322c832]com [b:979322c832]ClientDataSet[/b:979322c832], e só há um processamento no botão Gravar. Não é necessário usar uma transação nesse caso, pois ela é implícita (sem especificar transações, cada comando SQL gera sua própria). E, se for o caso de usar uma, evite [b:979322c832]CommitRetaining[/b:979322c832], principalmente em ambientes multi-usuários, pois isso mantém a transação aberta e pode gerar erros de dead-locks, dependendo do nível de isolamento adotado;

[b:979322c832]3)[/b:979322c832] No botão Cancelar, novamente por estar usando dbExpress + ClientDataSet, vc não precisa usar uma transação, pq tudo acontece em memória. O método [b:979322c832]Cancel [/b:979322c832]só vai desfaze as alterações feitas no DataSet, que ainda não foram gravadas no banco de dados. E, quando for usar [b:979322c832]Rollback[/b:979322c832], novamente evite o reter a transação após o comando ([b:979322c832]RollbackRetaining[/b:979322c832]);

Do mais seu código está bem organizado. Parabéns! ;-)

[]´s


Responder Citar

15/02/2006

Michael

Ah, é claro: vc sempre pode usar [b:b8c04b0d75]Stored Procedures[/b:b8c04b0d75] para aumentar a perfomance de grandes processamentos, ou até mesmo simples inserções ou edições. Embora muitos digam que não se ganhe nada nesses casos, isso ajuda vc a proteger o banco de dados, dando direitos de alteração a usuários apenas via SP´s.

[]´s


Responder Citar

15/02/2006

Rodrigorpb

[b:7be5417f1a]MUITO OBRIGADO PELA DICA, VALEU MESMO.[/b:7be5417f1a]


Outra coisa Uso IBQuery, IBUpdate e DataSource,


[b:7be5417f1a]Tem Alguma dica, ou é a mesma coisa do dbExpress e ClientDataSet.[/b:7be5417f1a]



Rodrigo


Responder Citar

15/02/2006

Rodrigorpb

Alguém saberia me dizer se com o IBQuery, IBUpdate e DataSource estas dicas funcionam.

Michael pode me dizer.

Rodrigo.


Responder Citar