Torna indietro   Hardware Upgrade Forum > Software > Programmazione

Sony INZONE H6 Air: il primo headset open-back di Sony per giocatori
Sony INZONE H6 Air: il primo headset open-back di Sony per giocatori
Il primo headset open-back della linea INZONE arriva a 200 euro con driver derivati dalle cuffie da studio MDR-MV1 e un peso record di soli 199 grammi
Nutanix cambia pelle: dall’iperconvergenza alla piattaforma full stack per cloud ibrido e IA
Nutanix cambia pelle: dall’iperconvergenza alla piattaforma full stack per cloud ibrido e IA
Al .NEXT 2026 di Chicago, Nutanix ha mostrato quanto sia cambiata: una piattaforma software che gestisce VM, container e carichi di lavoro IA ovunque, dall’on-premise al cloud pubblico. Con un’esecuzione rapidissima sulle partnership e sulla migrazione da VMware
Recensione Xiaomi Pad 8 Pro: potenza bruta e HyperOS 3 per sfidare la fascia alta
Recensione Xiaomi Pad 8 Pro: potenza bruta e HyperOS 3 per sfidare la fascia alta
Xiaomi Pad 8 Pro adotta il potente Snapdragon 8 Elite all'interno di un corpo con spessore di soli 5,75 mm e pannello LCD a 144Hz flicker-free, per un tablet che può essere utilizzato con accessori dedicati di altissima qualità. Fra le caratteristiche esclusive, soprattutto per chi intende usarlo con la tastiera ufficiale, c'è la modalità Workstation di HyperOS 3, che trasforma Android in un sistema operativo con interfaccia a finestre
Tutti gli articoli Tutte le news

Vai al Forum
Rispondi
 
Strumenti
Old 23-04-2012, 18:01   #1
RaouL_BennetH
Senior Member
 
L'Avatar di RaouL_BennetH
 
Iscritto dal: Sep 2004
Messaggi: 3967
[C# / Linq To Entities]Problema con duplicati

Buonasera a tutti.

Vorrei capire come rimuovere dei duplicati da una "query":

Codice:
using(GammaEntities context = new GammaEntities())
{
    var result = context.CustomView.Where
         (
            x.SomeValue == "BLA"
            && x.OtherValue != "BOB"
         )

     aBinding.BindingSource = result.OrderBy(x => x.aField);
}
In linea di massima ottengo tutti i risultati corretti eccetto un paio che mi
vengono restituiti duplicati.
Per duplicato intendo che è la stessa identica riga con gli stessi identici valori.

Grazie a tutti.

RaouL.
__________________
Dai wafer di silicio nasce: LoHacker... il primo biscotto Geek
RaouL_BennetH è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 18:19   #2
=KaTaKliSm4=
Senior Member
 
L'Avatar di =KaTaKliSm4=
 
Iscritto dal: Jul 2006
Città: Altamura
Messaggi: 919
Quote:
Originariamente inviato da RaouL_BennetH Guarda i messaggi
Buonasera a tutti.

Vorrei capire come rimuovere dei duplicati da una "query":

Codice:
using(GammaEntities context = new GammaEntities())
{
    var result = context.CustomView.Where
         (
            x.SomeValue == "BLA"
            && x.OtherValue != "BOB"
         )

     aBinding.BindingSource = result.OrderBy(x => x.aField);
}
In linea di massima ottengo tutti i risultati corretti eccetto un paio che mi
vengono restituiti duplicati.
Per duplicato intendo che è la stessa identica riga con gli stessi identici valori.

Grazie a tutti.

RaouL.
C'è un problema di fondo, se la query ritorna dati duplicati è perchè il database non è normalizzato, la tabella non ha chiavi primarie giusto?
__________________
Trattative : http://swdev.altervista.org/VenditeAcquisti.txt Blog Tecnico : http://blogs.dotnethell.it/SwDev/
Desktop : i7 920,GTX580 PALIT, Obsidian 800D, 6GB Corsair, OCZ Vertex 3 240gb.
Desktop 2 : iMac 27'' MID 2011 i5, 4GB
=KaTaKliSm4= è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 18:23   #3
RaouL_BennetH
Senior Member
 
L'Avatar di RaouL_BennetH
 
Iscritto dal: Sep 2004
Messaggi: 3967
Quote:
Originariamente inviato da =KaTaKliSm4= Guarda i messaggi
C'è un problema di fondo, se la query ritorna dati duplicati è perchè il database non è normalizzato, la tabella non ha chiavi primarie giusto?
Centro

Ma su questo purtroppo non abbiamo modo di agire. Il database in questione è solo una replica (su sql server 2008) di un db proprietario.
__________________
Dai wafer di silicio nasce: LoHacker... il primo biscotto Geek
RaouL_BennetH è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 18:32   #4
=KaTaKliSm4=
Senior Member
 
L'Avatar di =KaTaKliSm4=
 
Iscritto dal: Jul 2006
Città: Altamura
Messaggi: 919
Quote:
Originariamente inviato da RaouL_BennetH Guarda i messaggi
Centro

Ma su questo purtroppo non abbiamo modo di agire. Il database in questione è solo una replica (su sql server 2008) di un db proprietario.
Per caso è la replica di un gestionale?Per curiosità potresti farmi capire quale?Lavoro parecchio con le repliche DB, magari ho già lavorato con il DB in questione...

Comunque dovresti scriverti una classe comparer (eredita da IEqualityComparer) :

Codice:
class TuoRecordComparer : IEqualityComparer<TuoRecord> {

    public bool Equals(TuaEntità x, TuaEntità y) {
        return x.CampoA == y.CampoA && x.CampoB == y.CampoB && Etc... ;
    }

    public int GetHashCode(TuaEntità obj) {
        return obj.CampoA.GetHashCode() * obj.CampoB.GetHashCode();
    }
}
Ed utilizzarlo come argomento nel metodo Distinct :

Codice:
List<TuaEntità> res = TuaCollection.Distinct(new TuoRecordComparer());
Fammi sapere
__________________
Trattative : http://swdev.altervista.org/VenditeAcquisti.txt Blog Tecnico : http://blogs.dotnethell.it/SwDev/
Desktop : i7 920,GTX580 PALIT, Obsidian 800D, 6GB Corsair, OCZ Vertex 3 240gb.
Desktop 2 : iMac 27'' MID 2011 i5, 4GB
=KaTaKliSm4= è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 18:41   #5
RaouL_BennetH
Senior Member
 
L'Avatar di RaouL_BennetH
 
Iscritto dal: Sep 2004
Messaggi: 3967
per la "replica" hai pvt

Ora provo ad implementare il tuo suggerimento.
__________________
Dai wafer di silicio nasce: LoHacker... il primo biscotto Geek
RaouL_BennetH è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 18:49   #6
Kralizek
Senior Member
 
L'Avatar di Kralizek
 
Iscritto dal: Feb 2003
Città: Stockholm (SE)
Messaggi: 1343
un semplice distinct alla fine?

Codice:
using(GammaEntities context = new GammaEntities())
{
    var result = context.CustomView.Where
         (
            x.SomeValue == "BLA"
            && x.OtherValue != "BOB"
         )

     aBinding.BindingSource = result.OrderBy(x => x.aField).Distinct();
}
anche perché la classe che implementa IEqualityComparer<T> non verrebbe vista da EF forzandoti ad eseguire l'operazione in memory con L2Object invece che sul db
Kralizek è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 19:00   #7
RaouL_BennetH
Senior Member
 
L'Avatar di RaouL_BennetH
 
Iscritto dal: Sep 2004
Messaggi: 3967
Quote:
Originariamente inviato da Kralizek Guarda i messaggi
un semplice distinct alla fine?

Codice:
using(GammaEntities context = new GammaEntities())
{
    var result = context.CustomView.Where
         (
            x.SomeValue == "BLA"
            && x.OtherValue != "BOB"
         )

     aBinding.BindingSource = result.OrderBy(x => x.aField).Distinct();
}
anche perché la classe che implementa IEqualityComparer<T> non verrebbe vista da EF forzandoti ad eseguire l'operazione in memory con L2Object invece che sul db
Ciao

Avevo già provato con la distinct ma senza successo.

E ho provato anche a spostarlo "all'inizio"

Codice:
var result = context.Bla.Distinct().Where(blablabla);
__________________
Dai wafer di silicio nasce: LoHacker... il primo biscotto Geek
RaouL_BennetH è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 19:01   #8
=KaTaKliSm4=
Senior Member
 
L'Avatar di =KaTaKliSm4=
 
Iscritto dal: Jul 2006
Città: Altamura
Messaggi: 919
Quote:
Originariamente inviato da Kralizek Guarda i messaggi
un semplice distinct alla fine?

Codice:
using(GammaEntities context = new GammaEntities())
{
    var result = context.CustomView.Where
         (
            x.SomeValue == "BLA"
            && x.OtherValue != "BOB"
         )

     aBinding.BindingSource = result.OrderBy(x => x.aField).Distinct();
}
Non "dovrebbe" funzionare a rigor di logica, senza implementare un comparer, semplicemente perchè l'entità non ha chiavi primarie e non è possibile distinguere un oggetto da un altro.

E' vero, con il comparer l'operazione viene effettuata in memoria, ma non mi sembra un gran danno, ipotizando il numero di record.

L'unico modo per effettuare lo scarto dei duplicati direttamente sul DB è utilizzare una GroupBy a questo punto...

Codice:
var Res = TuaCollection.GroupBy(o => o.CampoA).Select(g => g.First());
__________________
Trattative : http://swdev.altervista.org/VenditeAcquisti.txt Blog Tecnico : http://blogs.dotnethell.it/SwDev/
Desktop : i7 920,GTX580 PALIT, Obsidian 800D, 6GB Corsair, OCZ Vertex 3 240gb.
Desktop 2 : iMac 27'' MID 2011 i5, 4GB
=KaTaKliSm4= è offline   Rispondi citando il messaggio o parte di esso
Old 23-04-2012, 20:26   #9
Kralizek
Senior Member
 
L'Avatar di Kralizek
 
Iscritto dal: Feb 2003
Città: Stockholm (SE)
Messaggi: 1343
Ma il distinct in SQL mica richiede la presenza di una chiave primaria...

Potresti postare la query generata da EF?

In alternativa potrebbe fare una projection dell'entity in un tipo anonimo, eseguire il distinct e convertire gli oggetti restituiti in entity.

Ovviamente in questo modo si perde il tracking automatico delle modifiche, ma quello era già buono ed andato con il comparer in memory
Kralizek è offline   Rispondi citando il messaggio o parte di esso
Old 24-04-2012, 08:39   #10
gugoXX
Senior Member
 
L'Avatar di gugoXX
 
Iscritto dal: May 2004
Città: Londra (Torino)
Messaggi: 3692
Il Distinct non funziona se non c'e' un comparer perche' 2 istanze diverse della stessa classe, anche quando contenessero gli stessi identici valori, sarebbero di per se' differenti in quanto risiedono su diverse zone di memoria e il comparer di default si basa proprio su quello.

Se per caso CustomView fosse una collezione di DataRow, puoi usare il comparer Standard delle DataRow

aBinding.BindingSource = result.Distinct(DataRowComparer.Default).OrderBy(x => x.aField);


Altrimenti anche io propenderei per la soluzione con il group by

var Res = result.GroupBy(o => o.CampoA)
.Select(g => g.First())
.OrderBy(x => x.aField);
__________________
Se pensi che il tuo codice sia troppo complesso da capire senza commenti, e' segno che molto probabilmente il tuo codice e' semplicemente mal scritto.
E se pensi di avere bisogno di un nuovo commento, significa che ti manca almeno un test.
gugoXX è offline   Rispondi citando il messaggio o parte di esso
Old 24-04-2012, 08:50   #11
Kralizek
Senior Member
 
L'Avatar di Kralizek
 
Iscritto dal: Feb 2003
Città: Stockholm (SE)
Messaggi: 1343
Quote:
Originariamente inviato da gugoXX Guarda i messaggi
Il Distinct non funziona se non c'e' un comparer perche' 2 istanze diverse della stessa classe, anche quando contenessero gli stessi identici valori, sarebbero di per se' differenti in quanto risiedono su diverse zone di memoria e il comparer di default si basa proprio su quello.

Se per caso CustomView fosse una collezione di DataRow, puoi usare il comparer Standard delle DataRow

aBinding.BindingSource = result.Distinct(DataRowComparer.Default).OrderBy(x => x.aField);


Altrimenti anche io propenderei per la soluzione con il group by

var Res = result.GroupBy(o => o.CampoA)
.Select(g => g.First())
.OrderBy(x => x.aField);
un tipo anonimo non ha un comparer definito a compile time che compara i valori?

Per provare ho eseguito questa query con LinqPad su un database che avevo a portata di mano:

Codice:
Institutes.Select(c => new 
{
	c.FKSiteID, c.IsPublished, c.HasLogo, c.FKUpdatedByID
}).Take(1000).Distinct().Dump();
ed l'sql risultante é correttamente

Codice:
SELECT DISTINCT [t1].[FKSiteID], [t1].[IsPublished], [t1].[HasLogo], [t1].[FKUpdatedByID]
FROM (
    SELECT TOP (1000) [t0].[FKSiteID], [t0].[IsPublished], [t0].[HasLogo], [t0].[FKUpdatedByID]
    FROM [institute].[Institutes] AS [t0]
    ) AS [t1]
A questo punto basta creare il tipo anonimo con tutti i campi della tabella, e dopo il distinct, ricreare le entities con un parameter-less constructor.

Ultima modifica di Kralizek : 24-04-2012 alle 08:56.
Kralizek è offline   Rispondi citando il messaggio o parte di esso
Old 24-04-2012, 10:56   #12
RaouL_BennetH
Senior Member
 
L'Avatar di RaouL_BennetH
 
Iscritto dal: Sep 2004
Messaggi: 3967
Eccomi

utilizzando il metodo GroupBy effettivamente i duplicati vengono rimossi, soltanto che, in particolari circostanze, ad esempio un numero fattura uguale per cliente o fornitore presenti nella vista (es. fatt cliente 156, fatt fornitore 156) mi da un solo record se il raggruppamento viene fatto sul numdoc (e non ho altri campi validi per raggruppare).

Credo che sia sbagliata proprio la progettazione della vista a monte ma su quella posso fare ben poco.

Per lo scopo ho dovuto risolvere in un'altra maniera:

1) I dati mi servivano per generare un tracciato record per l'agenzia delle entrate
2) Generato il tracciato record con tutti i duplicati, sono andato ad agire sul tracciato per rimuoverli mediante:

Codice:
File.WriteAllLine(@"trNoDup", lines.Distinct().ToArray());
Va a buon fine, nel senso che il controllo effettuato mediante entratel
non ne scarta più nessuno.
__________________
Dai wafer di silicio nasce: LoHacker... il primo biscotto Geek
RaouL_BennetH è offline   Rispondi citando il messaggio o parte di esso
Old 24-04-2012, 11:08   #13
=KaTaKliSm4=
Senior Member
 
L'Avatar di =KaTaKliSm4=
 
Iscritto dal: Jul 2006
Città: Altamura
Messaggi: 919
Quote:
Originariamente inviato da RaouL_BennetH Guarda i messaggi
Eccomi

utilizzando il metodo GroupBy effettivamente i duplicati vengono rimossi, soltanto che, in particolari circostanze, ad esempio un numero fattura uguale per cliente o fornitore presenti nella vista (es. fatt cliente 156, fatt fornitore 156) mi da un solo record se il raggruppamento viene fatto sul numdoc (e non ho altri campi validi per raggruppare).

Credo che sia sbagliata proprio la progettazione della vista a monte ma su quella posso fare ben poco.

Per lo scopo ho dovuto risolvere in un'altra maniera:

1) I dati mi servivano per generare un tracciato record per l'agenzia delle entrate
2) Generato il tracciato record con tutti i duplicati, sono andato ad agire sul tracciato per rimuoverli mediante:

Codice:
File.WriteAllLine(@"trNoDup", lines.Distinct().ToArray());
Va a buon fine, nel senso che il controllo effettuato mediante entratel
non ne scarta più nessuno.
A questo punto potevi utilizzare un comparer in memory....

L'importante è aver risolto, il principio del KISS è stato seguito alla perfezione

__________________
Trattative : http://swdev.altervista.org/VenditeAcquisti.txt Blog Tecnico : http://blogs.dotnethell.it/SwDev/
Desktop : i7 920,GTX580 PALIT, Obsidian 800D, 6GB Corsair, OCZ Vertex 3 240gb.
Desktop 2 : iMac 27'' MID 2011 i5, 4GB
=KaTaKliSm4= è offline   Rispondi citando il messaggio o parte di esso
Old 25-04-2012, 00:06   #14
gugoXX
Senior Member
 
L'Avatar di gugoXX
 
Iscritto dal: May 2004
Città: Londra (Torino)
Messaggi: 3692
Quote:
Originariamente inviato da Kralizek Guarda i messaggi
un tipo anonimo non ha un comparer definito a compile time che compara i valori?

Per provare ho eseguito questa query con LinqPad su un database che avevo a portata di mano:

Codice:
Institutes.Select(c => new 
{
	c.FKSiteID, c.IsPublished, c.HasLogo, c.FKUpdatedByID
}).Take(1000).Distinct().Dump();
ed l'sql risultante é correttamente

Codice:
SELECT DISTINCT [t1].[FKSiteID], [t1].[IsPublished], [t1].[HasLogo], [t1].[FKUpdatedByID]
FROM (
    SELECT TOP (1000) [t0].[FKSiteID], [t0].[IsPublished], [t0].[HasLogo], [t0].[FKUpdatedByID]
    FROM [institute].[Institutes] AS [t0]
    ) AS [t1]
A questo punto basta creare il tipo anonimo con tutti i campi della tabella, e dopo il distinct, ricreare le entities con un parameter-less constructor.
Vero, ma non lo farei.
Se dovesse cambiare la struttura della tabella/vista sottostante, alla meglio non compili, alla peggio potresti perdere qualche riga senza accorgertene.

Resta comunque una buona soluzione.
__________________
Se pensi che il tuo codice sia troppo complesso da capire senza commenti, e' segno che molto probabilmente il tuo codice e' semplicemente mal scritto.
E se pensi di avere bisogno di un nuovo commento, significa che ti manca almeno un test.

Ultima modifica di gugoXX : 25-04-2012 alle 00:22.
gugoXX è offline   Rispondi citando il messaggio o parte di esso
 Rispondi


Sony INZONE H6 Air: il primo headset open-back di Sony per giocatori Sony INZONE H6 Air: il primo headset open-back d...
Nutanix cambia pelle: dall’iperconvergenza alla piattaforma full stack per cloud ibrido e IA Nutanix cambia pelle: dall’iperconvergenza alla ...
Recensione Xiaomi Pad 8 Pro: potenza bruta e HyperOS 3 per sfidare la fascia alta Recensione Xiaomi Pad 8 Pro: potenza bruta e Hyp...
NZXT H9 Flow RGB+, Kraken Elite 420 e F140X: abbiamo provato il tris d'assi di NZXT NZXT H9 Flow RGB+, Kraken Elite 420 e F140X: abb...
ASUS ROG Swift OLED PG34WCDN recensione: il primo QD-OLED RGB da 360 Hz ASUS ROG Swift OLED PG34WCDN recensione: il prim...
Ecovacs presenta la gamma 2026: paviment...
Efficienza energetica fino a 2.000 volte...
Lenovo 360: il programma di canale dell'...
Appena 10.000 qubit per rompere la critt...
Analisi dei transistor durante il funzio...
Attacco informatico a Booking.com: espos...
A quattro mesi dal divieto dei social ne...
NVIDIA GeForce RTX 5060 e 5060 Ti: in ar...
Rebellions, Arm e SK Telecom, nuova alle...
Modernizzazione delle app: Red Hat OpenS...
Nel mirino di Google c'è il back ...
PRAGMATA in bundle con GeForce RTX 5000:...
Le novità MOVA per il 2026: robot e impi...
Windows, stop all'attivazione telefonica...
ASUS porta la serie TUF nel formato Mini...
Chromium
GPU-Z
OCCT
LibreOffice Portable
Opera One Portable
Opera One 106
CCleaner Portable
CCleaner Standard
Cpu-Z
Driver NVIDIA GeForce 546.65 WHQL
SmartFTP
Trillian
Google Chrome Portable
Google Chrome 120
VirtualBox
Tutti gli articoli Tutte le news Tutti i download

Strumenti

Regole
Non Puoi aprire nuove discussioni
Non Puoi rispondere ai messaggi
Non Puoi allegare file
Non Puoi modificare i tuoi messaggi

Il codice vB è On
Le Faccine sono On
Il codice [IMG] è On
Il codice HTML è Off
Vai al Forum


Tutti gli orari sono GMT +1. Ora sono le: 20:56.


Powered by vBulletin® Version 3.6.4
Copyright ©2000 - 2026, Jelsoft Enterprises Ltd.
Served by www3v