Zobrazit předchozí téma :: Zobrazit následující téma |
Autor |
Zpráva |
posila
Založen: 29. 07. 2007 Příspěvky: 201
|
Zaslal: 5. duben 2008, 18:27:54 Předmět: |
|
|
Ja bych se vykaslal na LINQ a nechal si to seradit metodou Sort tridy Array. Vypadalo by to nejak takto
kód: |
// vlastni comparer porovavajici DataRow podle zadanych sloupcu
class MyDataRowComparer : IComparer<DataRow>
{
string[] columns;
public MyDataRowComparer(string[] columns)
{
this.columns = columns;
}
int IComparer<DataRow>.Compare(DataRow x, DataRow y)
{
int compare = 0, i = 0;
while (compare == 0 && i < this.columns.Length)
{
compare = (x[this.columns[i]] as IComparable).CompareTo(y[this.columns[i]]);
i++;
}
return compare;
}
}
public static void Sort(DataRow[] rows, string[] columns)
{
Array.Sort(rows, new MyDataRowComparer(columns));
// neni treba nic vracet protoze Array.Sort je destruktivni
// (znici puvodni pole a nahradi ho serazenym)
}
|
Problem by nastal, kdyby v tom DataRow bylo neco, co neni comparable. |
|
Návrat nahoru |
|
|
posila
Založen: 29. 07. 2007 Příspěvky: 201
|
Zaslal: 6. duben 2008, 16:26:47 Předmět: |
|
|
Inu dobra . Ten prvni kod asi jen tak rozchodit nebude uplne snadne, protoze ten vnitrni vyraz vraci nejakou strasnou strukturu, ktera neni comparable. Ten druhy kod se uz da rozchodi pomerne lehce pridanim jednoho radku
kód: |
public static DataRow[] Sort(DataRow[] rows, string[] columns)
{
IOrderedEnumerable<DataRow> result;
result = rows.OrderBy(row => row[columns[0]]);
for (int i = 1; i < columns.Length; i++)
{
int j = i;
result = result.ThenBy(row => row[columns[j]]);
}
return result.ToArray();
} |
j bude mit platnost jen v ramci jednoho pruchodu cyklem a v dalsim pruchodu se vytvori nove. Jenomze v takovem pripade se clovek asi musi modlit, aby mu ho nekdy nesezral optimizer .
Jinak proti LINQu nic nemam, dokonce se mi docela libi , v tomhle pripade bych ho jen nepouzil.
Naposledy upravil posila dne 6. duben 2008, 16:34:42, celkově upraveno 1 krát |
|
Návrat nahoru |
|
|
rezna
Založen: 27. 07. 2007 Příspěvky: 2156
|
Zaslal: 6. duben 2008, 16:33:30 Předmět: |
|
|
se divam ze microsoft nam naboural zdrojaky a vytahl z nich vec kterou uz umime snad 5 let. |
|
Návrat nahoru |
|
|
posila
Založen: 29. 07. 2007 Příspěvky: 201
|
Zaslal: 6. duben 2008, 23:54:14 Předmět: |
|
|
Delal jsem pokus - vytovril jsem si pole delegatu a naplnil ho lamba funkcema :
kód: |
for (int i = 0; i < 10; i++)
{
d[i] = (x => x + i);
} |
a pak si to v dalsim cyklu nechal vypsat Console.WriteLine(d[i](0));. Clovek by nejdriv cekal, ze to vypise posloupnost 0 .. 9, jenze to vypsalo same 10. Kdyz se nad tim ale zamyslim, tak mi to prijde docela logicke. Ta lambda funkce bude normalni funkce zanorena v jine funkci, takze prejme z jejiho prostoru vsechny promenne. Tedy si nezapamatuje aktualni hodnotu i, ale pouziva i primo ze sveho rodice, ale ten muze i do zavolani lamda funkce zmenit. Tak nejak to vidim ja.
To, ze se to seradi spravne je spis podle me nahoda. Resp. zkus dat do vsech sloupcu stejne hodnoty a do sloupce odpovidajicimu coumns[1] ruzne hodnoty (ale v neusporadanem poradi). V takovem pripade by se to imho seradit nemelo. |
|
Návrat nahoru |
|
|
posila
Založen: 29. 07. 2007 Příspěvky: 201
|
Zaslal: 7. duben 2008, 21:33:08 Předmět: |
|
|
Ten trik s promennou j lokalni pro ten for cyklus by mel fungovat. Jeste dalsi moznost je si udelat comparable tridu, do ktere si ulozis do pole hodnoty ze sloupcu, ktere porovnavas... neco jako
kód: |
private class MyColumnComparable : IComparable<MyColumnComparable>
{
public object[] Data { set; get; }
public MyColumnComparable(IEnumerable<object> oe)
{
Data = oe.ToArray();
}
int IComparable<MyColumnComparable>.CompareTo(MyColumnComparable other)
{
int compare = 0, i = 0;
// pro jednoduchost spoleham na stejnou delku poli
while (compare == 0 && i < this.Data.Length)
{
compare = (this.Data[i] as IComparable).CompareTo(other.Data[i++]);
}
return compare;
}
}
public static DataRow[] Sort(DataRow[] rows, string[] columns)
{
var result = from row in rows orderby (new MyColumnComparable(from column in columns select row[column])) select row;
return result.ToArray();
} |
ale to je taky takove podivne reseni... fakt bych v tomhle pripade pouzil nejobycejnejsi Array.Sort |
|
Návrat nahoru |
|
|
|