Autore Topic: [RISOLTO] Delete record in tabella collegata  (Letto 3276 volte)

Offline naderit

  • Grande Gambero
  • ***
  • Post: 140
    • Mostra profilo
[RISOLTO] Delete record in tabella collegata
« il: 02 Maggio 2015, 08:41:14 »
Ciao a tutti, sono nuovamente a porre un quesito: ho due tabelle TAB1 e TAB2, in TAB1 ho un campo IDindex (Primary Key) i record di questa tabella non possono essere cancellati ma solamente modificati; in tabella TAB2 riporto il campo IDindex per poter collegare le tabelle. I record di TAB1 e TAB2 vengono visualizzati : TAB1 in GridView1 e con una query visualizzo in GridView2 i record della TAB2 collegati a un record di TAB1. E fino a questo punto tutto fila liscio. Ora il quesito:come posso eliminare un record di TAB2, tenendo presente che: il database viene aperto e chiuso di volta in volta, che in TAB2 non è presente una primary key e che i valori dei campi per record possono essere uguali. Ho pensato di utilizzare le istruzioni MoveTo, MoveLast ma non so se sono sulla strada giusta ho cercato anche nel forum ma non ho trovato molto.
Grazie
« Ultima modifica: 09 Maggio 2015, 14:35:30 da naderit »

Offline Berserker79

  • Grande Gambero
  • ***
  • Post: 201
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #1 il: 02 Maggio 2015, 18:02:39 »
Ciao, ma vuoi cancellare un record di n records con lo stesso IDindex?
Se i records nella tab2 non hanno una chiave primaria potresti usare il metodo update dell'oggetto data in cui carichi i dati con la query.
Se invece vuoi fare tutto tramite sql, potresti cancellare tutti i records con quell'IDindex e successivamente effettuare un insert con quelli rimasti nella gridview2.
Oppure metti una chiave primaria anche nella tab2 in modo da poter cancellare specificatamente quello che ti serve.

Offline vuott

  • Moderatore globale
  • Senatore Gambero
  • *****
  • Post: 11.705
  • Ne mors quidem nos iunget
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #2 il: 02 Maggio 2015, 20:36:02 »
Ho posto questa tua questione nel forum spagnolo:

http://www.gambas-es.org/viewtopic.php?f=3&t=4571
« Chiunque, non ricorrendo lo stato di necessità, nel proprio progetto Gambas fa uso delle istruzioni Shell o Exec, è punito con la sanzione pecuniaria da euro 20,00 a euro 60,00. »

Offline Picavbg

  • Senatore Gambero
  • ******
  • Post: 1.620
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #3 il: 02 Maggio 2015, 23:59:20 »
Ciao a tutti, sono nuovamente a porre un quesito: ho due tabelle TAB1 e TAB2.
in TAB1 ho un campo IDindex (Primary Key) i record di questa tabella non possono essere cancellati ma solamente modificati;
in tabella TAB2 riporto il campo IDindex per poter collegare le tabelle.
I record di TAB1 e TAB2 vengono visualizzati : in GridView1 i record della TAB1  e    con una query    visualizzo
                                                                    in GridView2 . i record della TAB2 collegati a un record di TAB1

come posso eliminare un record di TAB2, tenendo presente che: il database viene aperto e chiuso di volta in volta, che in TAB2 non è presente una primary key e che i valori dei campi per record possono essere uguali.

scusa se ho un pò modificato nella citazione del tuo post d'apertura l'ordine dei concetti da te esposti, ma l'ho fatto solamente per capire. Tuttavia non ho ancora completamente chiaro  il quesito.
Dalla tua esposizione, mi pare di capire che TAB2 possa contenere anche record diversi da quelli di presenti nella TAB1. O no?
Poi la cosa importante è che la Primary Key della TAB1 sia univoca, altrimenti il concetto di primary Key andrebbe a morire.

Per darti una mano, é perciò necessario che prima di tutto faccia capire meglio la relazione esistente fra le 2 TAB e se il DB contiene altre TAB, oltre alle due da te indicate nel post d'apertura.
 :ciao:
:ciao:

Offline naderit

  • Grande Gambero
  • ***
  • Post: 140
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #4 il: 03 Maggio 2015, 01:07:56 »
Ciao a tutti
provo a spiegarmi meglio: il database con cui lavoro è sqlite3, nella TAB1 ho una anagrafica con i campi :

IDsocio (Primary Key),Nome,Cognome,Indirizzo,Mail,Telefono.... ect
In TAB2 ho i seguenti campi:
IDsocio, anno, quota
in pratica creo una relazione "uno a molti" attraverso IDsocio, quindi in TAB2 posso avere n° record per un singolo IDsocio.

Codice: [Seleziona]

Public Sub GridView1_Click()
Dim rssoci As Result
Dim sql As String
Dim iRow As String

Dim id As Integer
Mod_conn.db_apro

iRow = GridView1.Row

sql = "SELECT * FROM soci" ' ordino la griglia
  rssoci = Mod_Conn.$conn.Exec(sql)
 
    If iRow <> -1 Then
           
            id = GridView1[iRow, 0].Text
         
            rssoci.MoveTo(id - 1)
            TextBox1.Text = rssoci[0] ' idsoci
            label1.Text = rssoci[2] 'nome
            label2.text = rssoci[3] 'tipo
            label3.Text = rssoci[4] 'telefono
            label4.Text = rssoci[5] 'cellulare
            label5.Text = rssoci[6] 'mail
            label6.Text = rssoci[7] 'titolo
   
Endif

  Mod_Conn.$conn.Close
  grid_quote
End

Public Sub grid_quote()
Dim rsquote As Result
Dim sql As String
Dim i As Integer
 
 GridView2.Clear 'pulisce griglia
 Mod_Conn.db_apro
 
  sql = "SELECT * FROM quote WHERE idsoci = '" & TextBox1.Text & "' "
  rsquote = Mod_Conn.$conn.Exec(sql)
   
     If rsquote.Available = True Then    ' controlla se la query ha dato dei risultati in caso affermativo procede alla visualizzazione
                                            'altrimenti visualizza messaggio di errore
                GridView2.Mode = Select.multiple
               
                GridView2.Columns.Count = 2              'imposta il numero di colonne della GridView1
                GridView2.Rows.Count = rsquote.Count         'imposta il numero di record in base al numero di risultati presenti
                i = 0
               
               
               
                For Each rsquote                                   'inizio del ciclo
                 
                  GridView2[i, 0].Text = rsquote!Anno
                  GridView2[i, 1].Text = Format$(rsquote!Importo, "$$0.#0")                'scrime il 1° valore nella griglia
                 
                 
                  Inc i          'aumenta di uno la variabile i in tal modo al prossimo ciclo si scrivera il record sucessivo
                 
                Next
     Else                                        ' nel caso hres non contenga risultati
                  GridView2.Columns.Count = 1
                  GridView2.Rows.Count = 1
                  GridView2[0, 0].Text = "Nessun dato"  'viene visualizzata la scritta "nessun dato"
         
     Endif
   Mod_Conn.$conn.Close
End

Con questo codice popolo la GridView2 per ogni record, ad ogni evento Click di GridView1, la domanda era come posso eliminare o modificare un record visualizzato in GridView2 quando in TAB2 ho per IDsoci ho più record con lo stesso valore, oppure lo stesso anno? ovvero come posso identificare il record selezionato in GridView2? Devo per forza creare una chiave primaria anche in TAB2? questa soluzione la vorrei evitare.
Belin come è tardi notte  ;D ;D




Offline Picavbg

  • Senatore Gambero
  • ******
  • Post: 1.620
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #5 il: 03 Maggio 2015, 10:03:56 »
Ciao a tuttila domanda era come posso eliminare o modificare un record visualizzato in GridView2 quando in TAB2 ho per IDsoci ho più record con lo stesso valore, oppure lo stesso anno? ovvero come posso identificare il record selezionato in GridView2? Devo per forza creare una chiave primaria anche in TAB2? questa soluzione la vorrei evitare.

No, non è necessario.
Posso suggerirti la soluzione adottata da me nel mio programma eterno di Contabilità familiare.
Riporto qui allegata un'immagine nella quale puoi riscontrare due aree, una superiore in cui ho posto la griglia coi dati provenienti dalla relativa tabella di DB SQLite o inseriti ex novo in digitazione, la parte inferiore in cui sono sistemate le caselle di testo occorrenti per le opportune modifiche, inserimenti o, al limite, eliminazione di righe superate per la giornata contabile in chiusura.

Il mio metodo funziona così: Alla presentazione della finestra, eseguo doppio click sulla riga della griglia da modificare o eliminare. La riga viene svuotata ed il suo contenuto, trasferito nelle Textbox, sottostanti la griglia. A questo punto posso intervenire modificando il contenuto di una o più caselle di testo, oppure, cliccando sul pulsante "Annulla digitazione corrente", posso eliminare definitivamente i dati provenienti dalla griglia. I dati modificati e, perciò, validi, vanno a riposizionarsi  nella riga originaria con  doppio 'INVIO' o cliccando sul pulsante 'OK'.

Nel tuo caso si aggiungerebbe un'occorrenza, quella di ricompattare,in caso di eliminazione del contenuto, le righe della griglia, dopo avere svuotato, di volta in volta, quelle selezionate e spostate per l'intervento necessario.

Se l'idea ti dovesse piacere, possiamo, se vuoi, approfondire il concetto.
 ;)
« Ultima modifica: 03 Maggio 2015, 10:15:56 da Picavbg »
:ciao:

Offline Gianluigi

  • Moderatore globale
  • Senatore Gambero
  • *****
  • Post: 4.244
  • Tonno verde
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #6 il: 03 Maggio 2015, 13:45:42 »
Scusate se mi intrometto pur non essendo un grande esperto di database.  :-[
Occorre però che vengano precisate alcune cose basilari che se non vengono rispettate porteranno il nostro database a miseri risultati.
SQLite è un database relazionale, questo comporta alcune semplici inderogabili regole:
1 - Relazionale significa che i dati vengono archiviati a gruppi in relazione fra di loro, insomma le tabelle (relazioni) devono contenere tutti i dati del database in relazione fra di loro. Questo significa che un dato non in relazione non può trovarsi in nessuna altra tabella salvo eccezioni particolare che qui non cito ma che ad esempio è la relazione fra tabelle uno a molti.
2 – Ogni record presente nel database deve per ovvi motivi di integrità essere identificato in modo univoco.

Sono molte altre le regole per costruire database relazionali robusti, e quelle che vi ho citato sono le più elementari.
« Ultima modifica: 03 Maggio 2015, 14:13:21 da Gianluigi »
nuoto in attesa del bacio di una principessa che mi trasformi in un gambero azzurro

Offline Picavbg

  • Senatore Gambero
  • ******
  • Post: 1.620
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #7 il: 03 Maggio 2015, 17:04:45 »
@ Gianluigi

Ho letto la tua più che corretta riflessione ed ho rivisto le note di  naderit riguardo ai contenuti delle due tabelle componenti il suo DB.
Non ho notato anomalie pratiche. La relazione fra le due tabelle esiste e si chiama IDsocio, le altre colonne delle suddette tabelle contengono dati non duplicati. L'unica cosa che manca è la primary Key nella Tab2, ma siccome la lettura di una tabella di DB in SQLite avviene con una formula tecnica che non richiede necessariamente la presenza di una primary key ( Es. preso dal mio programma: RecMovgg = ApriDB.DBConnection.EXEC("SELECT * FROM movimgg WHERE DtCoMovgg = '" & iDataCont & "' ORDER BY DtSolMovgg, OraSolMovgg") dove DtCoMovgg non é primary key della mia tabella movimgg, il problema della primary key nella TAB2 di naderit non sorge proprio.
In vero la primary key della sua Tab2 dovrebbe essere costituito dall'insieme dei due campi: IDsocio e anno, proprio per rispondere al corretto concetto dell'univocità della primary key. Considera inoltre che le due Tabelle, secondo quanto ho capito, non dispongono di alcuna chiave di indirizzamento, ma soltanto di un legame relazionale costituito dal campo IDsocio, perciò la gestione del DB  non comporterà alcun problema pratico di accesso.
Secondo me può proseguire tranquillo, senza alcun timore di malfunzionamento gestionale del DB.

Vorrei solo aggiungere un consiglio a naderit. Modificare la sua stringa di preparazione alla lettura della Tab1 così:
Codice: [Seleziona]
  sql = "SELECT * FROM soci ORDER BY IDsocio"         ' ordino la griglia
  rssoci = Mod_Conn.$conn.Exec(sql)
solamente allo scopo di evitare un elenco disordinato di soci, qualora la colonna IDsocio potesse contenere codici non tutti crescenti.
 :ciao:
:ciao:

Offline Gianluigi

  • Moderatore globale
  • Senatore Gambero
  • *****
  • Post: 4.244
  • Tonno verde
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #8 il: 03 Maggio 2015, 17:55:43 »
Caro @Picavbg

io volevo solo rammentare una regola basilare, si possono fare moltissime cose con i database e tantissime non sono propriamente corrette, non ho approfondito il codice di naderit, anche perché c'è Berserker79 e ci sei tu che di database ne sapete senz'altro più di me, ma non credo che basti la copia di campi come chiave, avendo lui parlato di relazione uno a molti, temo che per quel dato giorno siano appunto molti i dati relativi a quel socio.
Comunque il punto non è questo, visto che naderit sta iniziando io ho creduto giusto indicargli la retta via e la retta via è sicuramente quella che ogni record di un database deve essere univoco vale adire che deve essere facilmente identificato da una chiave, a prescindere che questa sia unica (cosa auspicabile perché più facilmente controllabile) o doppia, tripla ecc.
E poi scusa ma cosa costa aggiungere un contatore a una tabella? Si fa in un attimo e rendi tutto più semplice e rapido.
Infine per essere chiarissimo ribadisco a naderit che tu e Berserker79 di database ne sapete senz'altro più di me.  :-*  :D
 :ciao:
nuoto in attesa del bacio di una principessa che mi trasformi in un gambero azzurro

Offline Picavbg

  • Senatore Gambero
  • ******
  • Post: 1.620
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #9 il: 03 Maggio 2015, 22:12:24 »
@ Gianluigi,
ti ringrazio per il complimento , ma, se non l'hai dimenticato, forse non sai che fsurfing è un maestro, infatti mi ha insegnato a muovermi in SQLite.
A parte ciò non vorrei averti dato l'impressione di non avere apprezzato il tuo intervento. Ho solo approfitttao per mettere in chiaro alcuni aspetti, però SQLite non è un ambiente DB raffinato. Io inizialmente mi ero molto preoccupato sull'individuazione esatta delle primary key, considerando anche chiavi composte da più colonne, poi, quando ho capito che in effetti potevo gestirmi i criteri di relazionalità nelle istruzioni SELECT, ho deciso di assegnare il ruolo di chiave primaria ad un non necessario codice progressivo di numero di record, il cui compito è esclusivamente quello di sapere in ogni momento quante righe costituiscono ciascuna tabella del mio DB.
Quindi, scusami se ho dato l'impressione di apprezzare negativamente il tuo intervento. Tutti gli interventi sono costruttivi perché aiutano ad analizzare e considerare meglio nel dettaglio il problema posto dall'autore della discussione. Così come una discussione non serve solamente ad aiutare l'autore del post d'apertura, ma anche chi interviene successivamente.
Detto questo, vorrei cogliere l'ccasione per dare a naderit un'altra dritta: non è necessario definire la colonna relazionale fra due tabelle del DB lo stesso nome, nel suo caso 'IDsocio', perché tale criterio comporta un'ulteriore specificazione referenziale della tabella di appartenenza di ciascuna delle colonne interessate in certe query.
Nel caso di utilizzo di query che impegnino, per es. sia la TAB1 che la TAB2, asrebbe necessario specificare a quale tabella si riferisce il codice 'IDsocio':
Codice: [Seleziona]
  sql = "SELECT * FROM soci, quote ORDER BY soci.IDsocio,  quote.IDsocio, anno" 
. Diventa più semplice, per es. scrivere IDsocioT1, IDsocioT2, per distinguere quello interno alla Tab1 da quello interno alla Tab2.
 :ciao:

:ciao:

Offline vuott

  • Moderatore globale
  • Senatore Gambero
  • *****
  • Post: 11.705
  • Ne mors quidem nos iunget
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #10 il: 04 Maggio 2015, 14:54:49 »
naderit, è stata aggiunta una risposta:

http://www.gambas-es.org/viewtopic.php?f=3&p=26200#p26200
« Chiunque, non ricorrendo lo stato di necessità, nel proprio progetto Gambas fa uso delle istruzioni Shell o Exec, è punito con la sanzione pecuniaria da euro 20,00 a euro 60,00. »

Offline milio

  • Senatore Gambero
  • ******
  • Post: 1.273
  • Chi parla poco dice tanto...
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #11 il: 04 Maggio 2015, 21:22:20 »

e la retta via è sicuramente quella che ogni record di un database deve essere univoco vale adire che deve essere facilmente identificato da una chiave, a prescindere che questa sia unica (cosa auspicabile perché più facilmente controllabile) o doppia, tripla ecc.


Questo topic andava chiuso con un risolto solo dopo aver letto questa frase...  ;D

Sacro Sante parole... :ok:

Offline naderit

  • Grande Gambero
  • ***
  • Post: 140
    • Mostra profilo
Re: Delete record in tabella collegata
« Risposta #12 il: 04 Maggio 2015, 22:12:52 »
in realtà avrei già risolto in quanto GAMBAS mette a disposizione tutti gli strumenti :
usando il componente DataSource abbinato al DataBrowser ed inserendo le semplici istruzioni:

DataSource1.Table = "quote"
DataSource1.Filter = db.Subst("idsoci LIKE &1", TextBox1.text)

risolvendo egregiamente il problema, ma volevo seguire un'altra strada. E poi il bello della programmazione è non porsi limiti.. ;D ;D :ciao: :ciao: 

Offline naderit

  • Grande Gambero
  • ***
  • Post: 140
    • Mostra profilo
Re:[RISOLTO] Delete record in tabella collegata
« Risposta #13 il: 09 Maggio 2015, 14:34:20 »
Alla fine mi sono dovuto arrendere ad usare una ID primary key, anche se e possibile eliminare un record in questo modo:

Dim rsquote As Result
 Mod_Conn.db_apro ' collegamento al dbase
  rsquote = Mod_Conn.$conn.Exec("DELETE FROM miatabella WHERE campo1 = &1", valore1, "AND campo2 = &1", valore2)
Mod_Conn.$conn.Close

però dopo aver studiato SQLite sono arrivato alla conclusione che utilizzando una primary key mi facilita puntare la Row da eliminare o modificare,

rsquote = Mod_Conn.$conn.Exec("DELETE FROM miatabella WHERE IDcampo = &1", valore) 'IDcampo Primary Key

anche se l'idea che eliminare dei record con primary key non mi convinca pienamente.
 :ciao: :ciao:

Offline Gianluigi

  • Moderatore globale
  • Senatore Gambero
  • *****
  • Post: 4.244
  • Tonno verde
    • Mostra profilo
Re:[RISOLTO] Delete record in tabella collegata
« Risposta #14 il: 09 Maggio 2015, 16:03:47 »
Alla fine mi sono dovuto arrendere ad usare una ID primary key, anche se e possibile eliminare un record in questo modo:
Arreso e perché arreso? Questa che hai operato è l'unica scelta sensata, logica e naturale.
Citazione
anche se l'idea che eliminare dei record con primary key non mi convinca pienamente.
 :ciao: :ciao:

Questa proprio... cosa vorresti significare? Mi fai sorgere il dubbio che tu non abbia ben compreso che cosa è e a cosa serve una chiave primaria.
In un database relazionale fatto come Dio comanda ci sono due cose indispensabili in ogni tabella la chiave primaria che come detto potrebbe, volendosi complicare la vita, essere anche composita e la chiave esterna.
La chiave primaria serve appunto per identificare il record, e perché dobbiamo identificarlo? Per poterci lavorare che vuol dire anche poterlo eliminare.
 :ciao:
nuoto in attesa del bacio di una principessa che mi trasformi in un gambero azzurro