F-Droid bannerem na svých stránkách a také v aplikacích F-Droid a F-Droid Basic upozorňuje na iniciativu Keep Android Open. Od září 2026 bude Android vyžadovat, aby všechny aplikace byly registrovány ověřenými vývojáři, aby mohly být nainstalovány na certifikovaných zařízeních Android. To ohrožuje alternativní obchody s aplikacemi jako F-Droid a možnost instalace aplikací mimo oficiální obchod (sideloading).
Svobodná historická realtimová strategie 0 A.D. (Wikipedie) byla vydána ve verzi 28 (0.28.0). Její kódový název je Boiorix. Představení novinek v poznámkách k vydání. Ke stažení také na Flathubu a Snapcraftu.
Multimediální server a user space API PipeWire (Wikipedie) poskytující PulseAudio, JACK, ALSA a GStreamer rozhraní byl vydán ve verzi 1.6.0 (Bluesky). Přehled novinek na GitLabu.
UBports, nadace a komunita kolem Ubuntu pro telefony a tablety Ubuntu Touch, vydala Ubuntu Touch 24.04-1.2 a 20.04 OTA-12.
Byla vydána (Mastodon, 𝕏) nová stabilní verze 2.0 otevřeného operačního systému pro chytré hodinky AsteroidOS (Wikipedie). Přehled novinek v oznámení o vydání a na YouTube.
WoWee je open-source klient pro MMORPG hru World of Warcraft, kompatibilní se základní verzí a rozšířeními The Burning Crusade a Wrath of the Lich King. Klient je napsaný v C++ a využívá vlastní OpenGL renderer, pro provoz vyžaduje modely, grafiku, hudbu, zvuky a další assety z originální kopie hry od Blizzardu. Zdrojový kód je na GitHubu, dostupný pod licencí MIT.
Byl představen ICT Supply Chain Security Toolbox, společný nezávazný rámec EU pro posuzování a snižování kybernetických bezpečnostních rizik v ICT dodavatelských řetězcích. Toolbox identifikuje možné rizikové scénáře ovlivňující ICT dodavatelské řetězce a na jejich podkladě nabízí koordinovaná doporučení k hodnocení a mitigaci rizik. Doporučení se dotýkají mj. podpory multi-vendor strategií a snižování závislostí na vysoce
… více »Nizozemský ministr obrany Gijs Tuinman prohlásil, že je možné stíhací letouny F-35 'jailbreaknout stejně jako iPhony', tedy upravit jejich software bez souhlasu USA nebo spolupráce s výrobcem Lockheed Martin. Tento výrok zazněl v rozhovoru na BNR Nieuwsradio, kde Tuinman naznačil, že evropské země by mohly potřebovat větší nezávislost na americké technologii. Jak by bylo jailbreak možné technicky provést pan ministr nijak nespecifikoval, nicméně je známé, že izraelské letectvo ve svých modifikovaných stíhačkách F-35 používá vlastní software.
Nové číslo časopisu Raspberry Pi zdarma ke čtení: Raspberry Pi Official Magazine 162 (pdf).
Sdružení CZ.NIC, správce české národní domény, zveřejnilo Domain Report za rok 2025 s klíčovými daty o vývoji domény .CZ. Na konci roku 2025 bylo v registru české národní domény celkem 1 515 860 s koncovkou .CZ. Průměrně bylo měsíčně zaregistrováno 16 222 domén, přičemž nejvíce registrací proběhlo v lednu (18 722) a nejméně pak v červnu (14 559). Podíl domén zabezpečených pomocí technologie DNSSEC se po několika letech stagnace výrazně
… více »
Radujme se. Dokončil jsem konečně quicksort a je to opravdu o dost rychlejší než posledně. 1500 položek to seřadí během okamžiku. Funkce compare_*( FileInfo *fi1, FileInfo *fi2, bool ascending ) a sort( FileInfoList* list, int column, bool ascending ) jsou deklarovány jako chráněné a statické. K použití je určena veřejná fce sort( int column, bool ascending )
Budu rád za jakékoliv další návrhy vedoucí ke zrychlení.
int FileInfoList::compare_size( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
if( fi1->isDevice() && !fi2->isDevice() ) return -1 * asc;
if( fi2->isDevice() && !fi1->isDevice() ) return 1 * asc;
if( (fi1->isDir() && fi2->isDir()) || (fi1->isDevice() && fi2->isDevice()) ) return 0;
off64_t size1, size2;
fi1->getSize(size1);
fi2->getSize(size2);
if( size1 > size2 ) return 1 * asc;
if( size2 > size1 ) return -1 * asc;
return 0;
}
int FileInfoList::compare_name( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
return g_utf8_collate( fi1->getName().c_str(), fi2->getName().c_str() ) * asc;
}
int FileInfoList::compare_ext( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
if( fi1->isDevice() && !fi2->isDevice() ) return -1 * asc;
if( fi2->isDevice() && !fi1->isDevice() ) return 1 * asc;
if( (fi1->isDir() && fi2->isDir()) || (fi1->isDevice() && fi2->isDevice()) ) return 0;
return g_utf8_collate( fi1->getExt().c_str(), fi2->getExt().c_str() ) * asc;
}
int FileInfoList::compare_attrs( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
return g_utf8_collate( fi1->getAttrs().c_str(), fi2->getAttrs().c_str() ) * asc;
}
int FileInfoList::compare_owner( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
return g_utf8_collate( fi1->getOwner().c_str(), fi2->getOwner().c_str() ) * asc;
}
int FileInfoList::compare_group( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
return g_utf8_collate( fi1->getGroup().c_str(), fi2->getGroup().c_str() ) * asc;
}
int FileInfoList::compare_date( FileInfo *fi1, FileInfo *fi2, bool ascending )
{
int asc = ( ascending ? 1 : -1 );
if( fi1->isDots() ) return -1;
if( fi2->isDots() ) return 1;
if( fi1->isDir() && !fi2->isDir() ) return -1;
if( fi2->isDir() && !fi1->isDir() ) return 1;
time_t modDate;
struct tm tm1;
struct tm tm2;
struct tm *ctm;
fi1->getDate( modDate );
ctm = localtime( &modDate );
memcpy( &tm1, ctm, sizeof(tm1) );
fi2->getDate( modDate );
ctm = localtime( &modDate );
memcpy( &tm2, ctm, sizeof(tm2) );
if( tm1.tm_year > tm2.tm_year ) return 1 * asc;
if( tm1.tm_year < tm2.tm_year ) return -1 * asc;
if( tm1.tm_mon > tm2.tm_mon ) return 1 * asc;
if( tm1.tm_mon < tm2.tm_mon ) return -1 * asc;
if( tm1.tm_mday > tm2.tm_mday ) return 1 * asc;
if( tm1.tm_mday < tm2.tm_mday ) return -1 * asc;
if( tm1.tm_hour > tm2.tm_hour ) return 1 * asc;
if( tm1.tm_hour < tm2.tm_hour ) return -1 * asc;
if( tm1.tm_min > tm2.tm_min ) return 1 * asc;
if( tm1.tm_min < tm2.tm_min ) return -1 * asc;
if( tm1.tm_sec > tm2.tm_sec ) return 1 * asc;
if( tm1.tm_sec < tm2.tm_sec ) return -1 * asc;
return 0;
}
void FileInfoList::sort( FileInfoList* list, int column, bool ascending )
{
if( list->count() <= 1 ) return;
// false = dont free items
FileInfoList before( false );
FileInfoList behind( false );
FileInfoList same( false );
FileInfoList::size_type nCentral = list->count() / 2;
int compareRes;
for( FileInfoList::size_type i = 0; i < list->count(); ++i )
{
if( i == nCentral ){
same.push_back( list->at(nCentral) );
continue;
}
switch( column )
{
case 0:
compareRes = FileInfoList::compare_name( list->at(nCentral), list->at(i), ascending );
break;
case 1:
compareRes = FileInfoList::compare_ext( list->at(nCentral), list->at(i), ascending );
break;
case 2:
compareRes = FileInfoList::compare_size( list->at(nCentral), list->at(i), ascending );
break;
case 3:
compareRes = FileInfoList::compare_date( list->at(nCentral), list->at(i), ascending );
break;
case 4:
compareRes = FileInfoList::compare_attrs( list->at(nCentral), list->at(i), ascending );
break;
case 5:
compareRes = FileInfoList::compare_owner( list->at(nCentral), list->at(i), ascending );
break;
default:
compareRes = FileInfoList::compare_group( list->at(nCentral), list->at(i), ascending );
break;
}
if( compareRes == 0 ) same.push_back( list->at(i) );
if( compareRes > 0 ) before.push_back( list->at(i) );
if( compareRes < 0 ) behind.push_back( list->at(i) );
}
if(before.count()>1) FileInfoList::sort( &before, column, ascending );
if(behind.count()>1) FileInfoList::sort( &behind, column, ascending );
FileInfoList::size_type pos = 0;
for( FileInfoList::size_type i = 0; i < before.count(); ++i )
list->at(pos++) = before.at(i);
for( FileInfoList::size_type i = 0; i < same.count(); ++i )
list->at(pos++) = same.at(i);
for( FileInfoList::size_type i = 0; i < behind.count(); ++i )
list->at(pos++) = behind.at(i);
}
void FileInfoList::sort( int column, bool ascending )
{
sort( this, column, ascending );
}
Tiskni
Sdílej:
1. Klasický zásobník je samozřejmě rychlý, ale rekurzivní implementace na něj ukládá mnohonásobně víc dat, než je potřeba. Jeho velikost je navíc omezena a na některých platformách je to omezení dost výrazné. Navíc je to omezení, se kterým prostě nehnete.
2. Realokovat není (obecně) potřeba a není ani nutné alokovat obrovské pole předem. Zásobník totiž vůbec nemusí být realizován jako lineární pole.
3. Snadno nahlédneme, že paměťové nároky řešení s vlastním zásobníkem jsou už z principu nižší než paměťové nároky řešení pomocí rekurze. Navíc s tím rozdílem, že pokud dojde místo na systémovém zásobníku, máme smůlu; dojde-li místo v našem zásobníku, dá se s tím něco dělat.
Sečteno a podtrženo: než někoho nařknete, že o problematice nic neví, nebývá od věci ověřit, zda toho sám víte aspoň tolik co on. Vyhnete se tak zbytečné blamáži…
Zásobník totiž vůbec nemusí být realizován jako lineární pole.A třeba takový
std::stack ani není. Protože bývá typicky implementován pomocí std::deque, nepotřebuje souvislý úsek paměti.
#include <stdio.h>
int q(int i) {
printf("%d\n", i);
q(i+1);
}
int main(int argc, char** argv) {
q(0);
}
a nez to spadlo, tak napocital do 523 722. A dost pochybuju, ze by se algoritmus pri razeni nekolika souboru v adresari nekdy dostal do srovnatelny hloubky
A dost pochybuju, ze by se algoritmus pri razeni nekolika souboru v adresari nekdy dostal do srovnatelny hloubkyHehe. Takto by programátor uvažovat neměl.
, ale pokud provedu jenom hrubej vypocet, tak v idealnim pripade (pokud by se mu podarilo pole rozdelit vzdy presne na pul) by se do tyto hloubky dostal az pri poli velkym 2**523722 = 10e19 polozek. ono se mu to sice pravdepodobne vetsinou nepodari rozdelit presne na pul, ale stejne by to melo stacit na hodne hodne hodne velky pole...
2. A co takhle spojový seznam z jednotlivých polí vhodně zvolené velikosti? Realokovat není potřeba nic, alokovat nemusím tak často, overhead na spojovací pointer je zanedbatelný. Jinak ani kdyby to byl opravdu čistý spojový seznam, nemáte pravdu, protože ten pointer má z podstaty věci přesně stejnou velikost jako návratová adresa (kterou tam pro změnu nutně potřebujete vy) - a pořád ušetřím nějaké ty lokální proměnné.
3. Ne. Opakuji, že při rozumné implementaci zásobníku není potřeba nic realokovat.
Ad P.S.: porovnejte si celkovou velikost lokálních proměnných a argumentů u vašeho testovacího prográmku a u implementace, o níž tu byla řeč. Pořád sice zbyde relativně velké číslo, ale jak už jsem řekl, existují i jiné platformy.
Mimochodem, netvrdím, že rekurze je vždy špatná. Jen zásadně nesouhladím s důvody, které pro její upřednostnění uvádíte.
počet prvků = počet tříděných prvků / 2, tedy např. pro třídění pole int indexované int bude mít stejnou velikost, jako tříděné pole, pro třídění řetězců bude zabírat zlomek paměti zabrané tříděným seznamem. Opravdu monstrózní paměťové nároky…
Gcc umí aspoň tail recursion, aspoň občas, když už ne obecně.) Hromada rekurzivních volání jsou jen skoky s přejmenováním parametrů. Jak je to u quicksortu, to se budu muset podívat – docela mě to zajímá a už byh si ho měl konečně taky jednou naimplementovat.
Ale přesto mi přijde, že hromada lidí šmahem odsuzuje rekurzi proto, že nikdy neviděli kompilátor, který ji dokáže vyeliminovat. A přitom to může být tak pěkné (a bezpečné) goto s parametry...
btw, ked uz vykon (a pamat), radsej by som pouzil radix sort
int (*compare)(FileInfo *, FileInfo *, bool);
switch( column )
{
case 0:
compare = &FileInfoList::compare_name;
break;
case 1:
compare = &FileInfoList::compare_ext;
break;
case 2:
compare = &FileInfoList::compare_size;
break;
case 3:
compare = &FileInfoList::compare_date;
break;
case 4:
compare = &FileInfoList::compare_attrs;
break;
case 5:
compare = &FileInfoList::compare_owner;
break;
default:
compare = &FileInfoList::compare_group;
break;
}
for( FileInfoList::size_type i = 0; i < list->count(); ++i )
{
if( i == nCentral ){
same.push_back( list->at(nCentral) );
continue;
}
compareRes = (*compare)( list->at(nCentral), list->at(i), ascending );
/* ... */
a taky porovnavani ascending bych nepsal do kazdy compare fci zvlast ale primo do sort, je to min prace. ale to uz byl jenom takovej kosmetickej detail ;)
Co mne nejak nenapada, ale neni switch jenom if () { } else if () { } else { } ?Obecně být nemusí. Pokud bude kompilátor dostatečné chytrý, může to v řadě případů optimalizovat. Bohužel nevím, jestli to GCC dělá (případně které verze).
Je pravda, že virtual call něco stojí, ale v případě poměrně primitivních mechanismů C++ a relativně složitých porovnávacích funkcí, která vidím v kódu, mi to přijde docela levné. A líp by se to četlo.
) problému, ale právě jsem se vrátil z...společenské události...
...a vůbec, budu se potřebovat pořádně vyspat.
Ovšem po čtení knihy Thinking Forth (ve které každá třetí věta obsahuje sloveso „factor out“
) cestou domů ovšem působí takovýhle kód prostě jako rána palici do hlavy.
Nemluvě o tom, že už jsem asi hodně odvykl používání Windows, takže samotná myšlenka dělení jména souboru na jméno a příponu mi připadá poněkud nepatřičná…
2. Jeslti dobře vidím, porovnáváte timestampy tak, že je převedete struct time a ty pak složitě porovnáváte po složkách. Nebylo by praktičtější porovnat je rovnou nebo, bojíte-li se tolik o přenositelnost na obskurní platformy, použít difftime()?
isDots(), dostanete vždy -1.
class Comparator;
class CompareFileSize : Comparator; // atd
class FileListInfo {
public static COMPARE_BY_FILE_SIZE;
}
FileInfoList::sort (const Comparator &);
...
file_list->sort (FileListInfo->COMPARE_BY_FILE_SIZE);
file_list->sort (new MyCrazyComparator);
file_list->reverse;
public static COMPARE_BY_FILE_SIZE;asi něco chybí.

file_list->sort(new MyCrazyComparator);Typická ukázka ztracení pointeru (leda, že by pak ta fce na konci volala delete).
) ved ich nechajme, nech sa hraju
)
FileInfoList má členskou funkci, která umí setřídit jinou instanci FileInfoList a pak další členskou funkci, která té první předá svou instanci. To je poněkud avantgardní řešení, ne?
void FileInfoList::sort( FileInfoList* list, int column, bool ascending )
{
…
}
void FileInfoList::sort( int column, bool ascending )
{
sort( this, column, ascending );
}
Zajímavé.
sort(), ale řekl bych, že to je ve srovnání s paměťovou náročností spíše vedlejší problém.
if( list->count() <= 1 ) return;
int (*compare)(FileInfo *, FileInfo *, bool);
switch( column )
{
case 0:
compare = FileInfoList::compare_name;
break;
case 1:
compare = FileInfoList::compare_ext;
break;
case 2:
compare = FileInfoList::compare_size;
break;
case 3:
compare = FileInfoList::compare_date;
break;
case 4:
compare = FileInfoList::compare_attrs;
break;
case 5:
compare = FileInfoList::compare_owner;
break;
default:
compare = FileInfoList::compare_group;
break;
}
#define MAX_LEVELS 1000
FileInfo *piv;
int beg[MAX_LEVELS], end[MAX_LEVELS];
int i=0, L, R, elements = (int)list->count();
beg[0] = 0;
end[0] = elements;
while(i>=0)
{
L = beg[i];
R = end[i] - 1;
if( L < R )
{
if( i == MAX_LEVELS - 1 ) return;
piv = list->at(L);
while( L < R )
{
while(compare(list->at(R),piv,ascending) >= 0 && L<R ) R--;
if(L<R) list->at(L++) = list->at(R);
while(compare(list->at(L),piv,ascending) <= 0 && L<R ) L++;
if(L<R) list->at(R--) = list->at(L);
}
list->at(L) = piv;
beg[i+1] = L+1;
end[i+1] = end[i];
end[i++] = L;
} else {
i--;
}
}
template<typename Item>
void qsort(Item* a, int left, int right, int (*less)(Item a, Item b)) {
int i = left;
int j = right;
Item pivot = a[(i+j)/2];
while(i <= j) {
while(less(a[i], pivot)) i++;
while(less(pivot, a[j])) j--;
if(i < j) {
Item temp = a[i];
a[i] = a[j];
a[j] = temp;
i++; j--;
} else
if(i == j) {
i++; j--;
}
}
if(left < j) qsort(a, left, j, less);
if(i < right) qsort(a, i, right, less);
}
less je funkce, ktera prima dva prvky pole a vraci nenulovou hodnotu, pokud je prvni mensi nez druhy (ma byt v poli pred druhym)
podle me ta posloupnost neni naprosto nahodna, ale je pravdepodobny, ze bude uz castecne serazena
Navíc nevím nic o tom, jak jsou data udržována a obnovována, takže jsem raději vynechal naprosto běžné situace typu přidání nebo přejmenování jednoho souboru.
Další (menší) zdroj neefektivity je i v tom, že se používá at() místo operátoru [], čímž se zbytečně pokaždé testují meze.
bool compare_abc(const FileInfo* a, const FileInfo* b)
{
...
}
static bool (*compare_functions[]) = {
compare_abc,
compare_def,
...
}
inline void FileInfoList::sort() {
sort(begin(), end(), compare_functions[column]);
}
static bool (*compare_functions[])(const FileInfo* a, const FileInfo* b) = {
static bool (*compare_functions[])(const FileInfo*, const FileInfo*) = {
class file_comparator {
protected:
bool ascending;
virtual bool less(const FileInfo* a, const FileInfo* b) = 0;
public:
file_comparator(bool asc) : ascending(asc) {}
virtual ~file_comparator() {}
bool operator () (const FileInfo* a, const FileInfo* b);
};
bool file_comparator::operator () (const FileInfo* a, const FileInfo* b)
{
if (b->isDots()) return false;
if (a->isDots()) return true;
if (a->isDir() && !b->isDir()) return true;
if (b->isDir() && !a->isDir()) return false;
return (ascending ? less(a,b) : less(b,a));
}
class file_comparator_name : public file_comparator {
protected:
virtual bool less(const FileInfo* a, const FileInfo* b);
public:
file_comparator_name(bool asc) : file_compararator(asc) {}
virtual ~file_comparator_name() {}
};
bool file_comparator_name::less(const FileInfo* a, const FileInfo* b)
{
// tady porovnáme jména
}
// a podobně pro další kritéria
void FileInfoList::sort(FileInfoList::column_t column, bool asc)
{
file_comparator* cmp;
switch(column) {
case col_name:
cmp = new file_comparator_name(asc); break;
// ...
default:
// cannot happen
// throw ...;
}
std::sort(begin(), end(), cmp);
delete cmp;
}
(určitě jsou tam chyby, psal jsem to z hlavy a nezkoušel přeložit)
nevraviac o tom, ze v pripade vektora ci double-linked-list je to operacia urcite menej narocna.
. a .. vypisovaly vždy na začátku, pak ostatní adresáře a pak teprve ostatní typy souborů. Tím by se i obracení seznamu trochu zkomplikovalo. Kdyby šlo o prosté otočení pořadí, vůbec nejjednodušší by bylo nepřerovnávat nic a pouze ten seznam v opačném pořadí vypisovat…
to by som radsej pouzil nejake filtre (v design pattern terminologii by to boli pravdepodobne dekoratory nad zoznamom), a/alebo miesto komparatora pouzit key-generator (hmm, asi tiez dekoratory, ale nad prvkami zoznami)
priklady key-generatory:
- pre kazdy sortovatelny prvok
- case sensitivity/insensitivity
- ignorovat/neignorovat non-word character na zaciatku retazca
- file extension
FileList head = FileList->search ('.', '..');
FileList tail = FileList->search (mask)->filter (head);
tail->filter (new OwnerOnlyFilter)->sort (new FileListNameKey);
....
Panel.show (head + tail);
teraz ma tak napadlo, ze vlastne chyba definicia chovania v pripade rovnosti kriteria (typu primarne podla mtime, potom size, potom reverzne name)
typedef shared_ptr< FileInfo > FileInforPtr;
class RuntimeFileCmp {
public:
enum cmp_mode {default_mode, size_mode, name_mode, ext_mode, attrs_mode, owner_mode, group_mode, date_mode};
private:
cmp_mode mode_; //column
bool ascending_;
int FileInfoList::compare_size(const FileInforPtr &fi1, const FileInforPtr &fi2) const;
int FileInfoList::compare_name( const FileInforPtr &fi1, const FileInforPtr &fi2) const;
int FileInfoList::compare_ext( const FileInforPtr &fi1, const FileInforPtr &fi2) const ;
int FileInfoList::compare_attrs( const FileInforPtr &fi1, const FileInforPtr &fi2) const;
int FileInfoList::compare_owner( const FileInforPtr &fi1, const FileInforPtr &fi2) const;
int FileInfoList::compare_group( const FileInforPtr &fi1, const FileInforPtr &fi2) const;
int FileInfoList::compare_date( const FileInforPtr &fi1, const FileInforPtr &fi2)const;
public:
RuntimeFileCmp( cmp_mode m = default_mode, bool ascending = true ) : mode_( m ), ascending_( a )
{
}
void setComparisonMode( cmp_mode m = default_mode ){
mode_ = m;
}
cmp_mode getComparisonMode() const {
return mode_;
}
void setOrderingMode( bool a = true ){
ascending_ = a;
}
bool getOrderingMode() const {
return ascending_;
}
bool operator()( const FileInforPtr fi1, const FileInforPtr fi2 ) const
{
switch( mode_ )
{
case 0:
compareRes = compare_name( fi1, fi2 );
break;
case 1:
compareRes = compare_ext( fi1, fi2);
break;
case 2:
compareRes = compare_size( fi1, fi2 );
break;
case 3:
compareRes = compare_date( fi1, fi2 );
break;
case 4:
compareRes = compare_attrs( fi1, fi2 );
break;
case 5:
compareRes = compare_owner( fi1, fi2);
break;
default:
compareRes = compare_group( fi1, fi2);
break;
}
return compareRes > 0;
}
};
typedef std::set< FileInforPtr, RuntimeFileCmp > file_set_t; //kontejner XY
/////////////////////////////////////////////////////////////
//v kodu
RuntimeFileCmp<slo by to udelat i obecne> compareDate(RuntimeFileCmp::date_mode, false);
RuntimeFileCmp compareName(RuntimeFileCmp::name_mode, true);
file_set_t fileSetCompName( comapreName );
file_set_t fileSetCompDate( compareDate );
fileSetCompName a fileSetCompDate se sami seradi, kdyz budu chtit jiny zpusob, tak set priradim jinymu;
nebo pouzit komparator RuntimeFileCmp pro funkci std::sort, tj. data budou ve vektoru a ty vzdy seradim podle
toho jak vytvorim objekt k razeni, tj. RuntimeFileCmp.
Vse by se navic dalo parametrizovat. Je tu vyhoda oddelenych dat a algoritmu, navic, kdyz uz jsou napsany...
switch. Spíš bych volil řešení využívající polymorfismu, tj. něco podobného jako jsem navrhoval zde.