Newsgroup: it.comp.appl.access
Titolo: Duplicati non ammessi su due tabelle con access 2007

Salve a tutti,
vi pongo subito il  mio problema:
ho creato una maschera chiamata MSC_Elenco_Assistiti, come foglio dati in elenco con all'interno dell'intestazione maschera i vari pulsanti di comando come, inserisci nuovo, cancella, ecc... .
Quando clicco sul pulsante inserisci nuovo, si apre una maschera chiamata MSC_Assistiti in modalità popup, con al suo interno i dati dell'assistito presi dalla tabella TBL_Assistiti e in fondo alla stessa maschera ho inserito una sottomaschera chiamata SMSC_RelazioneParentela collegata alla tabella TBL_RelParentela.
Nella maschera popup ci sono iseriti i soliti campi Nome, Cognome, data di nascita, ecc... ed anche il codice fiscale.
Mentre nella sottomaschera oltre ad esserci la relazione di parentela come Marito, Figlio ecc... c'è anche il codice fiscale del parente, ovviamente che fa parte della tabella TBL_RelParentela, ovviamente le due tabelle sono in relazione tra di loro con il campo "ID" .
Quando clicco sul pulsante nuovo assistito e si apre la maschera MSC_Assistito con al suo interno la sottomaschera SMSC_RelazioneParentela, vado ad inserire i vari dati e quando arrivo ad inserire il codice fiscale (già settato nella tabella a: Indicizzato con duplicati non ammessi) al momento di cliccare sul tasto invio vorrei che mi controllasse sulle due tabelle collegate nella maschera e sottomaschera non ci sia un codice fiscale duplicato. Avvisandomi con una maschera di attenzione se voglio visualizzare la scheda di riferimento che si sta cercando di duplicare.
Questo è tutto.  Chiedo a chi mi puoi aiutare che codice vb devo inserire per avere questa funzione.
Grazie a tutti.

on 22-10-14, ..:: GiGhEn ::.. supposed :

Ma in quante altre tabelle hai inserito quel CF munito già di
PK nella tabella principale? e per quale motivo?
Se hai correttamente relazionato le tabelle che portano il campo
CF, non hai alcuna necessità di controllarne eventuali duplicazioni,
già rese impossibili dal layout delle tabelle.
 
Bruno




Ho creato due tabelle e sono queste:
TBL_Assistiti
TBL_RelParentela
 
Due maschere e sono queste:
MSC_Assistiti
MSC_Elenco_Assistiti
 
Una sottomaschera ed è questa:
SMSC_RelParentela
 
Le due maschere hanno una relazione con ID Assistito una a molti
 
Tutte e due le tabelle hanno un campo  con CF al momento riesco ad evitare di duplicare solo il CF della tabella assistiti ma non in contemporaneo anche la tabella RelParentela che a sua volta contiene anche li un CF del parente dell'assistito.
 
Solo per la maschera assistiti sono riuscito a trovare un codice che mi funziona solo per gli assistiti della maschera MSC_Assisiti, ma non so come far filtrare contemporaneamente anche la sottomaschera,  riporto sotto il codice che ho inserito nella maschera al campo CF:
-----------------------
Private Sub Codice_Fiscale_BeforeUpdate(Cancel As Integer)
If DCount("CodiceFiscale", "TBL_Assistiti", "CodiceFiscale='" & CodiceFiscale & "'") > 0 Then
 
    If MsgBox("Attenzione l'assistito con questo codice fiscale è già esistente! Vuoi vedere i dati?", vbYesNo) = vbYes Then
          Set rs = CurrentDb.OpenRecordset("Select TOP 1 * From TBL_Assistiti where CodiceFiscale='" & CodiceFiscale & "' ORDER BY Cognome DESC")
          'In questo modo selezioni l'ultimo assistito inserito
          If Not rs.EOF Then
 
                 ID = rs.Fields("ID")
                 DataRegistrazione = rs.Fields("DataRegistrazione")
                 NumeroTesserino = rs.Fields("NumeroTesserino")
                 Cognome = rs.Fields("Cognome")
                 Nome = rs.Fields("Nome")
                 DataNascita = rs.Fields("DataNascita")
                 CodiceFiscale = rs.Fields("CodiceFiscale")
                 Indirizzo = rs.Fields("Indirizzo")
                 Quartiere = rs.Fields("Quartiere")
                 Città = rs.Fields("Città")
                 CAP = rs.Fields("CAP")
                 Provincia = rs.Fields("Provincia")
                 Professione = rs.Fields("Professione")
                 PensioneSociale = rs.Fields("PensioneSociale")
                 PensioneINPS = rs.Fields("PensioneINPS")
                 TelefonoAbitazione = rs.Fields("TelefonoAbitazione")
                 TelefonoCellulare = rs.Fields("TelefonoCellulare")
                 NumeroComponenti = rs.Fields("NumeroComponenti")
                 Annotazioni = rs.Fields("Annotazioni")
 
 
          End If
 
         rs.Close
 
    Else
         Cancel = True
   End If
End If
End Sub
------------------

 TBL_RelParentela
[...]
 
Qual è il nome del campo che in TBL_Assistiti accoglie il CF?
Vi hai apposto una PK (chiave primaria)?
 
Qual è il nome del campo che in TBL_RelParentela accoglie il CF
dell'assistito? è questo CF che qui non deve apparire più di una volta?
 
Hai inserito Relazioni fra le due tabelle? se sì, quali?
 
Bruno

 "ID" . 
 
ovviamente non troppo.
perche' usi il campo id se hai gia' il codice fiscale che e' univoco?
 
se non hai gia' una chiave univoca ha senso 'inventare' un identificativo 
ma in questo caso la chiave univoca e' pure singolo campo quindi non e' 
vantaggioso usare l'id.
 
come mai hai fatto questa scelta?
 
[cut]
 
 
-- 
Paolo opg
 
BE AWARE that this post uses a fake reply-to address
to contact me write to:
janickg ( at ) hotmail ( dot ) com
--

 
 
se ho capito il tuo obiettivo, vuoi impedire che una persona registrata 
in tbl_assistiti possa essere registrato in tbl_relparentela.
 
scenario non troppo impossibile:
- mio padre mi accompagna da voi; io sono l'assistito e lui viene 
registrato nella tbl_relparenetela.
- mia mamma accompagna mio papa'; mio papa' e' l'assistito e il programma 
impedisce la sua registrazione come assistito perche' lo trova gia' 
censito nella tabella tbl_relparentela.
 
e' uno scenario plausibile?



  Si in effetti se il papà è registrato come assistito nella relazione di parentela ci sarà la moglie e il figlio, ma se domani viene a registrarsi la moglie come assistito il marito poi dovrebbe stare nella relazione parentela, cosa che non può avvenire in una famiglia perchè ci deve essere solo un assistito per famiglia e non che si registra tutta la famiglia come assistito.
In effetti per farla breve faccio parte della Croce Rossa Italiana Comitato Provinciale di Napoli e facciamo la distribuzione dei viveri e vestiario ai più bisognosi, per cui distribuiamo solo per nucleo familiare ed essendo a Napoli ci è capitato che qualcuno ha fatto il furbo, mentre con il sistema di registrazione e tesseramento che sto facendo, in ogni famiglia deve esistere solo un tesserato. 
Ora penso di essermi spiegato bene.


 
 
una soluzione che a me piace di piu' e' una struttura cosi':
 
tbl_persona
cf
nome
cognome
parent_cf
parent_relazione
 
tutti vengono registrati nella tbl_persona.
se cambia l'assistito (muore qualcuno, uno dei figli mette su famiglia,
etc) non devi spostare i dati da una tabella all'altra o fare
cancellazioni per consentire la registrazione o aggiornare la
situazione. se qualcuno cambia nucleo famigliare ti basta aggiornare il
parent_* per essere a posto 
 
per capire chi e' in relazione con chi, dato il cf dell'assistito:
 
select cf,cognome,nome,parent_relazione
from tbl_persona p
where 
p.cf
=cf dell'assistito or p.parent_cf = cf dell'assistito



 Mi spiace ora non posso più cambiare per il semplice motivo che sono gia inseriti tutti gli assistiti.
Ti riporto il mio schema del Dbase.
 
Tabelle: 
TBL_Assistiti
---------------
ID
DataRegistrazione
NumeroTesserino
Cognome	
Nome
DataNascita
LuogoNascita
CodiceFiscale
Indirizzo
Quartiere	
Città
CAP
Provincia
Professione
PensioneSociale
PensioneINPS
TelefonoAbitazione
TelefonoCellulare
NumeroComponenti	
Annotazioni
--------------
TBL_RelParentela
---------------
ID_RelPar
ID_Ass
RelParentela
RelParCognome
RelParNome
RelParDataNascita
CodFIsc
--------------------
Maschere:
------------------
MSC_Assistiti
MSC_Elenco_Assistiti
-------------------
Sottomaschera:
--------------------
SMSC_RelParentela
---------------------
La maschera MSC_Assistito contiene la Sottomaschera SMSC_RelParentela 
Ora hai il Dbase completo sul CF Assistito quando clicco invio mi deve controllare che non esiste lo stesso CF sia nella tabella TBL_Assistiti e sia nella tabella TBL_RelParentela, se esiste, non deve farmelo inserire e mi deve visualizzare la scheda con il CF che sto tentando di inserire come duplicato.
Posso solo modificare il DBase ma non posso ricrearlo altrimenti si ferma tutto e cisarebbe da reinserire tutti i dati  dentro.
Se possibile vorrei poter fare queste piccole modifiche.
Ciao e grazie della tua disponibilità.


 nella tabella TBL_RelParentela, se esiste
 
Vado a tasto, non certo perché abbia ben compreso quel che hai scritto.
 
Prima di aggiornare una scheda che contiene un Codice Fiscale
nel campo denominato per esempio CF, vuoi essere avvertito
se quel Codice Fiscale è già presente nel campo CodiceFiscale
di TBL_Assistiti e/o nel campo CodFisc di TBL_RelParentela.
 
Prova così:
======================================
Private Sub Form_BeforeUpdate(Cancel As Integer)
Dim db As Database, SQL As String, CodF(1 To 2) As String
Dim TableName(1 To 2) As String
Dim RS As Recordset, n(1 To 2) As Integer, i As Integer
 
Set db = CurrentDb
TableName(1) = "TBL_Assistiti":     CodF(1) = "CodiceFiscale"
TableName(2) = "TBL_RelParentela":  CodF(2) = "CodFisc"
 
For i = 1 To 2
    SQL = "SELECT " & TableName(i) & "." & CodF(i) & " From " & 
TableName(i)
    SQL = SQL & " WHERE (((" & TableName(i) & "." & CodF(i) & ")='" & 
[CF] & "'));"
    Set RS = db.OpenRecordset(SQL, dbOpenDynaset)
    If RS.RecordCount > 0 Then
        RS.MoveLast
        n(i) = RS.RecordCount
    End If
Next
 
If n(1) + n(2) Then
    Cancel = True
    MsgBox "Il Codice Fiscale " & [CF] & " è contenuto" & vbCrLf & _
           n(1) & " volte in TBL_Assistiti" & vbCrLf & _
           n(2) & " volte in TBL_RelParentela"
    SendKeys "{ESC}", True
End If
 
End Sub
========================================
 
Bruno


Ciao, e buongiorno:
ho fatto come mi hai consigliato, ma quando inserisco il codice che mi hai proposto
queste due righe (riportate sotto) si colorano di rosso, ma lascio come sta e provo lo stesso 
il codice, provo a mettere un CF duplicato e mi esce una finestra con questo avviso di errore e mi riporta al codice 
(che ho riportato sotto) evidenziato in blu:
 
Questo è il messaggio riportato dall'avviso.
 
"Errore di compilazione"
"Errore di sintassi"
 
E questo è il codice che mi si evidenzia in blu.
 
SQL = "SELECT " & TableName(i) & "." & CodF(i) & " From " &
 
SQL = SQL & " WHERE (((" & TableName(i) & "." & CodF(i) & ")='" &
[CF] & "'));"
 
Dov'è l'errore!?


Scusa ho trovato l'errore e l'ho risolto era che il codice deve essere su una sola riga e non da capo.
Però ne esce un'altro errore ed è questo:
 
"Errore di nun-time '2465' 
impossibile trovare il campo '|' a cui si fa riferimento.
Qui non so cosa fare

 rosso, ma lascio come sta e provo lo stesso 
 
Eccetera. Cosi' non ne esci facilmente. Il fatto e' che hai 
sbagliato all' inizio  perche'  quello  che  tu aiuti non e'
l' individuo ma, effettivamente, la famiglia. 
 
Dunque hai semplicemente bisogno di una tabella fatta cosi' : 
campo_kiave = codice_fiscale del tizio
campo_famiglia : un codice diverso da famiglia a famiglia che 
si ripete per ogni componente della famiglia. Lo scegli tu in
qualche modo ma ti consigierei di avere una tabella famiglie 
con campo_kiave = codice famiglia per controllare che quando 
crei un' altra famiglia non sbatti in una ripetizione.
 
Piu' altri campi a piacere tuo che sicuramente ti serviranno. 
 
Quando arriva un tizio qualunque (con o senza tessera) ti fai 
semplicemente  dare  il  suo codice fiscale e lo inserisci in 
maschera. Questa maschera  ti deve solo dire l' ultima data a 
cui hai dato le vettovaglie a quella famiglia e con quella ti 
regoli immediatamente. Se la data e' abbastanza vecchia (imposti
una misura automatica) procedi alla consegna e inserisci data e 
famiglia nella tabella "consegne". 
 
Quindi 3 tabelle : famiglie, individui, consegne. E non ti 
sbagli piu'.
 
Visto che e'per una buona causa sarei disposto a farti tutto
io gratis. Anche a trasferire i dati dalla vecchia tua struttura
a questa nuova. Il problema e' che io vivo a Roma. Come si fa ? 
 
 
 


Ciao, grazie della tua bontà e disponibilità, certo se non hai problemi a rifare tutto da capo potresti cimentarti a rifare tutto da capo e poi me lo puoi inviare via email che trovi in questo post, oppure troveremo un'altro modo.
Grazie e fammi sapere.

 Grazie e fammi sapere.
 
Se ti sta bene la logica che ho cercato di delinearti (ti sta bene ? 
Ho colto nel segno ? Sei sicuro ? Non vorrei fare un lavoro inutile,
tu mi capisci) dovresti mandarmi il tuo DB a questo indirizzo :
 
radica...@gmail.com
 
 
Cosi' intanto mi rendo conto di quanto lavoro dovro' fare per trasferire
i dati dal vecchio al nuovo.
 
Poi costruisco la nuova applicazione, la testo, ci carico i tuoi dati e 
te la mando. 
 
A quel punto pero' (a meno che tu non sia estremamente sveglio, cosa 
che mi pare tu sia) dovro' farti vedere come funziona. Beh ... Magari 
faro' un salto a Napoli. 
 
Se tutto va bene  questa  applicazione  la  potrai (la potremo) donare
a tutti i centri come il tuo. 
 
Attendo

 Qui non so cosa fare
Io ho riprodotto tabelle con nomi di campo esattamente
come tu hai indicati, e la procedura funziona perfettamente.
 
Certamente non ho considerato che il CF sia scritto su due righe
e ho supposto che il controllo della scheda sia denominato
"CF" e non diversamente.
Quindi non so che dirti.
 
Bruno


Per il trasferimento dei dati ci posso pensare anche io, anche per evitare di appesantire l'allegato dell'email.
Per quanto riguarda la donazione mi sta anche bene purchè nel programma ci sia il nostro nome.
Quando ti passo il DB devi fare in modo che sia molto simile a quello che ho creato, non lo chiedo io ma le signore della sezione femminile della cri e devo stare alle loro richieste anche della loro incompetenza.
Se poi nel frattempo ci sono delle modifiche man,mano te le faccio sapere.
Ciao ora ti invio il programma.


OK! Funziona alla perfezione, il controllo CF lo dovevo cambiare in CodiceFiscale ed è andato alla perfezione, solo che nell'avviso oltre a farmi vedere il CF, mi deve uscire anche il nominativo a chi appartiene compreso il numero del tesserino e pertanto non è possibile inserire tale assistito.
Risolvendo questo abbiamo copletato di tutto l'aiuto che mi interessava.

 Risolvendo questo abbiamo copletato di tutto l'aiuto che mi interessava.
 
Mi devi indicare QUALI CAMPI di TBL_Assistiti vuoi
rappresentati assieme al codice fiscale duplicato.
 
Bruno


Cognome e NumeroTesserino

..:: GiGhEn ::.. brought next idea :

===================================
Private Sub Form_BeforeUpdate(Cancel As Integer)
Dim db As Database, SQL As String, CodF(1 To 2) As String
Dim TableName(1 To 2) As String, S As String
Dim RS As Recordset, n(1 To 2) As Integer, i As Integer
 
Set db = CurrentDb
TableName(1) = "TBL_Assistiti":     CodF(1) = "CodiceFiscale"
TableName(2) = "TBL_RelParentela":  CodF(2) = "CodFisc"
S = "Il Codice Fiscale  " & Format(UCase([CodiceFiscale]), _
    "@@@ @@@ @@@@@ @@@@@") & "  è contenuto" & vbCrLf
 
For i = 1 To 2
    SQL = "SELECT " & TableName(i) & "." & CodF(i) & " From " & 
TableName(i)
    SQL = SQL & " WHERE (((" & TableName(i) & "." & CodF(i) & ")='" & 
[CodiceFiscale] & "'));"
    Set RS = db.OpenRecordset(SQL, dbOpenDynaset)
    If RS.RecordCount > 0 Then
        RS.MoveLast
        n(i) = RS.RecordCount
        S = S & n(i) & "  volte in  " & TableName(i) & vbCrLf
    End If
Next
 
If (n(1) + n(2)) > 0 Then
    SQL = "SELECT " & TableName(1) & "." & CodF(1) & ", " & 
TableName(1) & ".Cognome, "
    SQL = SQL & TableName(1) & ".Nome, " & TableName(1) & 
".NumeroTesserino "
    SQL = SQL & "From " & TableName(1) & " GROUP BY " & TableName(1) & 
"." & CodF(1) & ", "
    SQL = SQL & TableName(1) & ".Cognome, " & TableName(1) & ".Nome, "
    SQL = SQL & TableName(1) & ".NumeroTesserino "
    SQL = SQL & "HAVING (((" & TableName(1) & "." & CodF(1) & ")='" & 
[CodiceFiscale] & "'));"
    Set RS = db.OpenRecordset(SQL, dbOpenDynaset)
    MsgBox S & vbCrLf & RS![Cognome] & vbCrLf & RS![Nome] & _
               vbCrLf & RS![NumeroTesserino]
    Cancel = True
    SendKeys "{ESC}", True
    SendKeys "{ESC}", True
End If
 
End Sub
=======================================
 
Bruno


Mi scuso con il ritardo della mia risposta, purtroppo sono stato ammalato per diversi giorni e quando sono rientrato ho dovuto recuperare il lavoro arretrato e così ora che sono più libero ho ripreso a finire questo db.
Ritornando al progetto del db ho inserito il codice che mi hai proposto sopra nel campo CF che se digitavo un CF esistente cliccando su INVIO mi comparisse il messaggio che chiedevo e funziona alla perfezione, vorrei però apportare alcune modifiche aggiuntive (dopo aver inserito alcune mie piccole modifiche) e sono queste:
il messaggio riporta queste parole:
-------------------------
ATTENZIONE! (da capo)
Il codice fiscale NNNNNNN (da capo)
è già registrato 1 volta nella scheda TBL_Assistiti (da capo)
 
ROSSI
GIUSEPPE
0001
---------------------------
Oltre alle mie piccole modifiche che ho fatto nella posizione del testo, vorrei che nel messaggio invece di uscire quello che ho riportato sopra, mi uscisse questo:
------------------------
ATTENZIONE! (in un altro colore, in neretto, caratteri più grandi e al centro della finestra)
Il codice fiscale: NNNNNNN 
è già registrato a nome di:
 
Cognome:    ROSSI (in neretto)
Nome:       GIUSEPPE (in neretto)
N.Tesserino:0001 (in neretto)
 
Vuoi modificare questo?    (pulsanti) SI/NO
-------------------------------------------
NB: se si mi deve riportare nella scheda del sig. rossi al primo record per poterlo modificare, altrimenti mi riporta sul record che stavo inserendo per correggere l'errore.
 
Sperando di non arrecarti tanto fastidio ti ringrazio della tua pazienza e disponibilità.
 

..:: GiGhEn ::.. presented the following explanation :

Programmando sono disposto a perdere ore nella soluzione di un
problema di logica, ma nemmeno un minuto nei giochini di
valore estetico.
 
Alla prossima
Bruno


Grazie lo stesso.

 Ciao ora ti invio il programma.
 
Ma roba da pazzi :-) 
Vai ad aiutare la gente, vai ... 
 
Vabe'.