|
[ Valerij Zajcev @ 05.11.2010. 09:31 ] @
| Prica pocinje ovako ...
Code:
var queryOne = .....select new ... // neke vrednosti
Sada tu imam datume neke 1,2,5,7, gde fale 3,4,6...
Ja napravim jedan niz sa svim datumima od najmanjeg do najveceg koji se nalaze u queriju i napravion sa novi ...
Code:
var missingDates = .....select new ... // sve isto kao u queryOne dodelim vrednosti i sada imam te dve kolekcije
I sada probam...
Code:
var t = queryOne.Union(missingDates); // ovo nece da prodje ni compile
A probao sam i queryOne da castujem u IList i onda napravio novi objekat..
Code:
var newObj = new { sve isto kao sto je dodato u queryOne };
I probao da ovo dodam u listu pukne neki error na dodavanju prijavljuje...
Code:
The value "System.Linq.Enumerable+WhereSelectEnumerableI....f__AnonymousType9...and cannot be used in this generic collection.
Parameter name: value
Malo mi gori pod nogama pa ako neko ima ideju sta da uradim nek se javlja :(
|
[ mmix @ 05.11.2010. 09:50 ] @
izlgeda kao da dva anonymous new generisu dva razlicita tipa, to mozes lako proveriti debuggerom (vidi oba IQueryable<T> sta je T)
jedno od resenja je da ne koristis anonymous tipove, deklarisi klasu koja ima polja koja ti trebaju i uradi select new MojaKlasa onda ce T uvek biti isto.
[ Valerij Zajcev @ 05.11.2010. 10:13 ] @
Kada krenem kroz debug imam...
Code:
queryOne = {System.Linq.Enumerable+<JoinIterator>d__61`4[XXX.YYY.BLL.Order,XXX.YYY.BLL.OrdersStatus,System.Int32,<>f__AnonymousTypea`2[XXX.YYY.BLL.Order,XXX.YYY.BLL.OrdersStatus]].Join(value(XXX.YYY.BLL...
queryTwo = {System.Linq.Enumerable+WhereSelectEnumerableIterator`2[XXX.YYY.BLL.Order,<>f__AnonymousType9`19[System.String,System.String,System.Int32,System.String,System.Nullable`1[System.DateTime],System.String,System.String,System.String,System.Strin...
Predpostavljam da je to, to. Razlikuju se (ne znam jos ucim LINQ). Morao sam da zamenim XXX.YYY... ali dobro to su namespace-ovi nebitno je.
Mislis da ne koristim 'var'? A sta da koristim? Jer code koji vec postoji koristi ovaj pristup (var). Vec postoji klasa "Order" ali zbog silnih dodataka morali su ranije da koriste LINQ sada ja samo nastavljam :)
[ mmix @ 05.11.2010. 10:37 ] @
ma jok, var je ok, problem je sto ne moze da merguje liste instanci dva razlicita tipa a to je posledica anonymous tipova koji iako sadrze ista polja nisu isti tip. ako mergujes List<Anonmous1> i List<Anonmous2> sta bitrebao da bude rezultat
Dakle samo umesto sto projektujes u anonymous tipove projektuj u istu custom klasu, umesto
Code:
var result = from u in db.users
where nesto
select new {ID = u.id, Name = u.name };
var result2 = from u in db.users
where nesto2
select new {ID = u.id, Name = u.name };
// merge result i result2 ne radi
ide
Code:
class User { int ID {get; set;} string Name { get; set; }}
var result = from u in db.users
where nesto
select new User {ID = u.id, Name = u.name };
var result2 = from u in db.users
where nesto2
select new User {ID = u.id, Name = u.name };
// merge result i result2
jedini downside je sto moras da deklarises User klasu
primer sam lupio jer nisi izneo ceo svoj kod, ali pretpostavljam da vidis na sta ciljam
[ Majestic @ 05.11.2010. 11:15 ] @
Citat: Valerij Zajcev: Kada krenem kroz debug imam...
Code:
queryOne = {System.Linq.Enumerable+<JoinIterator>d__61`4[XXX.YYY.BLL.Order,XXX.YYY.BLL.OrdersStatus,System.Int32,<>f__AnonymousTypea`2[XXX.YYY.BLL.Order,XXX.YYY.BLL.OrdersStatus]].Join(value(XXX.YYY.BLL...
queryTwo = {System.Linq.Enumerable+WhereSelectEnumerableIterator`2[XXX.YYY.BLL.Order,<>f__AnonymousType9`19[System.String,System.String,System.Int32,System.String,System.Nullable`1[System.DateTime],
System.String,System.String,System.String,System.Strin...
Predpostavljam da je to, to. Razlikuju se (ne znam jos ucim LINQ). Morao sam da zamenim XXX.YYY... ali dobro to su namespace-ovi nebitno je.
Mislis da ne koristim 'var'? A sta da koristim? Jer code koji vec postoji koristi ovaj pristup (var). Vec postoji klasa "Order" ali zbog silnih dodataka morali su ranije da koriste LINQ sada ja samo nastavljam 
Evo da nadopunim Miljana sa kratkim sadrzajem vezanim za ovo tvoje. Mozda ti pomogne u razumijevanju i sprijeci
muke u buducnosti
http://www.speedyshare.com/files/25033007/CSharp30.zip
[ Valerij Zajcev @ 05.11.2010. 13:14 ] @
Citat: mmix: ma jok, var je ok, problem je sto ne moze da merguje liste instanci dva razlicita tipa a to je posledica anonymous tipova koji iako sadrze ista polja nisu isti tip. ako mergujes List<Anonmous1> i List<Anonmous2> sta bitrebao da bude rezultat ;)
Dakle samo umesto sto projektujes u anonymous tipove projektuj u istu custom klasu, umesto
Code:
var result = from u in db.users
where nesto
select new {ID = u.id, Name = u.name };
var result2 = from u in db.users
where nesto2
select new {ID = u.id, Name = u.name };
// merge result i result2 ne radi
ide
Code:
class User { int ID {get; set;} string Name { get; set; }}
var result = from u in db.users
where nesto
select new User {ID = u.id, Name = u.name };
var result2 = from u in db.users
where nesto2
select new User {ID = u.id, Name = u.name };
// merge result i result2
jedini downside je sto moras da deklarises User klasu
primer sam lupio jer nisi izneo ceo svoj kod, ali pretpostavljam da vidis na sta ciljam
To je resilo problem :)
Imam jos jedno pitanje. Kada kazem...
Code:
var merge = res1.Union(res2);
Dobijem samo da se ova dva rezultata spoje u jedan.
res1 - datumi iz baze
res2 - datumi koji ne postoje u bazi, a postoje izmedju i trebam da ih dodam
Dakle da li moze nekako u LINQ u toku izvrsavanja merge = ... da se proveri da li datum postoji u res1 ili ne?
[ mmix @ 05.11.2010. 13:27 ] @
Mozes
Union ima overload koji prima IEqualityComparer<T>
Napravis comparer klasu koji poredi User na osnovu datum polja (opet lupam)
Code (csharp):class MojUserEqualityComparer: IEqualityComparer<User>
{
public bool Equals(User b1, User b2)
{
return b1.datum == b2.datum;
}
public int GetHashCode(User u)
{
return u.datum.GetHashCode();
}
}
onda instancu toga ubacis u Union
Code (csharp):var merge = res1 .Union(res2, new MojUserEqualityComparer ());
Iskreno nemam pojma zasto ovde ne postoji labmda overload, ali ajde.
[ Boris B. @ 06.11.2010. 02:01 ] @
>>Iskreno nemam pojma zasto ovde ne postoji labmda overload, ali ajde.
Pa hajde da ga napravimo
Default implementacija IEqualityComparer koja prima lambde:
Code:
public class DefaultEqualityComparer<T> : IEqualityComparer<T>
{
private Func<T, T, bool> _equalsFunc;
private Func<T, int> _getHashCodeFunc;
public DefaultEqualityComparer(Func<T, T, bool> equalsFunc, Func<T, int> getHashCodeFunc)
{
_equalsFunc = equalsFunc;
_getHashCodeFunc = getHashCodeFunc;
}
public bool Equals(T x, T y)
{
return _equalsFunc(x, y);
}
public int GetHashCode(T obj)
{
return _getHashCodeFunc(obj);
}
}
Extension metod:
Code:
public static class Extensions
{
public static IEnumerable<T> Union<T>(this IEnumerable<T> enumerable, IEnumerable<T> second, Func<T, T, bool> equalsFunc, Func<T, int> getHashCodeFunc)
{
return enumerable.Union(second, new DefaultEqualityComparer<T>(equalsFunc, getHashCodeFunc));
}
}
upotreba:
Code:
var merge = res1.Union(res2, (x, y) => x.Datum == y.Datum, (x) => x.Datum.GetHashCode());
[ mmix @ 06.11.2010. 07:22 ] @
Dal union uopste poziva hasher? Kad si vec napravio extension zabodi breakpoint 
[ Valerij Zajcev @ 12.11.2010. 11:49 ] @
Ok, sada sam video da ivde postoji jedan problem.
Code:
var res1 = ....linq...select new OrderHelper{...
var res2 = ....linq...select new OrderHelper{...
var merge = res1.Union(res2, new OrderEqualityHelper());
U ovom trenutku, u obe liste je Order helper objekat, stim sto res1 sadrzi objekte koje imaju podatke, a res2 sadrzi isto samo sto su od propertija popunjani samo datumi. U debug-u provereno. Ali kada udje u OrderEqualityHelper() u metodi Equals oba parametra su isti. Naisao sam na dodatni problem pri spajanju pa sam ovo video. Moja pretpostavka je da bi u oh2 trbeala sva polja osim datuma da budu null osim datuma...?
Code:
public class OrderEqualityComparer : IEqualityComparer<OrderHelper>
{
public bool Equals(OrderHelper oh1, OrderHelper oh2)
{
return (oh1.Date == oh2.Date);
}
[ mmix @ 12.11.2010. 11:53 ] @
Nisam bas razumeo sta je isto?
oh1 i oh2 su ista referenca?
[ Valerij Zajcev @ 12.11.2010. 12:07 ] @
Code:
var unionResult = result1.Union(result2, new OrderEqualityComparer());
Na ovoj gore liniji
result1 sadrzi listu objekata cija su polja:
ID = 5, TypeID = 12, Date = 1/1/2010 ...
result2 sadrzi listu objekata cija su polja:
ID = 0, TypeID = 0, Date = 8/8/2010 ...
Ali kada udjem u metodu "Equals", kapiram da bi oh1 treba da sadrzi objekat iz result1, a oh2 objekat iz result2. Ali nije tako. Svaki objekat i u oh1 i u oh2 ima sve podatke kao da je ista lista :(
[ mmix @ 15.11.2010. 08:01 ] @
Jel sigurno svaki put?
Moze da bude da od dve liste pravi trcecu tako sto prvo ubaci elemente prve pa elemente druge?
[ Valerij Zajcev @ 22.11.2010. 07:22 ] @
Citat:
Jel sigurno svaki put?
Sory sto nisam odgovorio... Da svaki put se nekako ubace neki podaci u drugu listu i onda umesto da tamo budu samo datumi ono budu i datumi sa nekim pdoacima iz prve liste, nisam ukapirao sto. Ali problem sam resio drugacije posto su mi trebali nedostajuci datumi odradio sam ovako nesto, i radi.
Code:
var range = Enumerable.Range(0, (int)(maxDate - minDate).TotalDays + 1)
.Select(i => minDate.AddDays(i));
var missing = range.Except(onlyDatesFromResult1List);
List<DateTime> missingDatesList = missing.ToList();
Copyright (C) 2001-2025 by www.elitesecurity.org. All rights reserved.
|