Premium Реклама Spotlight Bundles Boost Банери Кредити
Основно Начало Сървъри Marketplace Форум Сървъри
Общности Хостинг Добави Auction Boost
Ресурси
Библиотеки Карти Видеа Магазин Bundles
Инструменти
Builder Demo CFG HUD
AMXX API
Вход Регистрация
TOP SERVER
[IG] Easy Surf | Ramp Fix | RANKS | REPLAYS
Counter-Strike 1.6
surf_flyin_fortress
40.160.19.36:27015
18.05 18:49
8/64
186ms
/ Библиотеки / celltravtrie.inc

celltravtrie.inc

string/array duality - bad idea but there's a bug

.inc 9.2 KB 351 реда 04.04.2026
Pawn / AMX Mod X
#if defined _cell_travtrie_included
 #endinput
#endif
#define _cell_travtrie_included

#include <cellarray>
#include <celltrie>

enum TravTrie
{
	Invalid_TravTrie = 0
}

#define TRAVTRIE_MAX_KEY_LEN 1024

stock g_Key[TRAVTRIE_MAX_KEY_LEN]
stock g_Value[TRAVTRIE_MAX_KEY_LEN]

stock TravTrie:TravTrieCreate(keylength = 64, startsize = 32)
{
	new Trie:tmp = TrieCreate();
	TrieSetCell(tmp, "", _:ArrayCreate(keylength, startsize));
	return TravTrie:tmp;
}

stock TravTrieDestroy(&TravTrie:trie)
{
	new Array:iter;
	if(!TrieGetCell(Trie:trie,"",any:iter)) { TrieDestroy(Trie:trie); return; }

	ArrayDestroy(iter);
	TrieDestroy(Trie:trie);
}

stock bool:TravTrieSetCell(TravTrie:trie, const key[], any:value)
{
	if(key[0] == '^n') return false;
	
	new any:val;
	if(!TravTrieGetCell(trie, key, val) )
	{
		new Array:iter;
		if(!TrieGetCell(Trie:trie,"",any:iter)) return false;
	
		ArrayPushString(Array:iter,key);
	}
	if(key[0] == '^n') return false;
	
	TrieSetCell(Trie:trie,key,value);
	return true;
}

stock bool:TravTrieSetArray(TravTrie:trie, const key[], const array[], num_items)
{
	if(key[0] == '^n') return false;
	
	new val[2];
	// string/array duality - bad idea but there's a bug
	if(!TravTrieGetArray(trie, key, val,sizeof(val)) )
	{
		new Array:iter;
		if(!TrieGetCell(Trie:trie,"",any:iter)) return false;
	
		ArrayPushArray(iter,key);
	}
	
	if(key[0] == '^n') return false;
	
	TrieSetArray(Trie:trie,key,array,num_items);
	return true;
}

stock bool:TravTrieSetString(TravTrie:trie, const key[], const value[])
{
	if(key[0] == '^n') return false;
	
	new val[4];
	if(!TravTrieGetString(trie, key, val,sizeof(val)) )
	{
		new Array:iter;
		if(!TrieGetCell(Trie:trie,"",any:iter)) return false;
	
		ArrayPushString(iter,key);
	}
	
	if(key[0] == '^n') return false;
	
	TrieSetString(Trie:trie,key,value);
	return true;
}

stock bool:TravTrieGetCell(TravTrie:trie, const key[], &any:value)
{
	return (key[0] == '^n') ? false : TrieGetCell(Trie:trie,key,value);
}

stock bool:TravTrieKeyExists(TravTrie:trie, const key[])
{
	return (key[0] == '^n') ? false : TrieKeyExists(Trie:trie,key);
}

stock bool:TravTrieGetArray(TravTrie:trie, const key[], any:array[], num_items)
{
	return (key[0] == '^n') ? false : TrieGetArray(Trie:trie,key,array,num_items);
}

stock bool:TravTrieGetString(TravTrie:trie, const key[], value[], max_size)
{
	return (key[0] == '^n') ? false : TrieGetString(Trie:trie,key,value,max_size);
}

stock bool:TravTrieDeleteKey(TravTrie:trie, const key[])
{
	if(key[0] != '^n' && TrieDeleteKey(Trie:trie,key) )
	{
		new Array:iter;
		if(!TrieGetCell(Trie:trie,"",any:iter)) return false;
	
		static tmp[TRAVTRIE_MAX_KEY_LEN];
		new index = 0;

		while(index < ArraySize(iter) )
		{
			ArrayGetString(iter, index, tmp, TRAVTRIE_MAX_KEY_LEN - 1);
			if(equal(tmp,key)) return (ArrayDeleteItem(iter, index) == 1);
			index++;
		}
	}
	return false;
}

stock TravTrieClear(TravTrie:trie)
{
	new Array:iter;
	if(!TrieGetCell(Trie:trie,"",any:iter)) { TrieClear(Trie:trie); return; }

	ArrayClear(iter);
	TrieClear(Trie:trie);
}

//stock TravTrieSize(TravTrie:trie) return TrieGetSize(trie) - 1;

// Rukia: Use this to prepare the TravTrie for SORTED traversal
//	If you do not use this, it will be traversed in FIFO order
stock bool:PrepareTravTrie(TravTrie:trie) 
{
	new Array:iter;
	if(!TrieGetCell(Trie:trie,"",any:iter)) { TrieClear(Trie:trie); return; }

	ArraySort(iter, "SortADTArrayDesc");
}

public SortADTArrayDesc(Array:array, item1, item2, const data[], data_size)
{
	static item1str[TRAVTRIE_MAX_KEY_LEN], item2str[TRAVTRIE_MAX_KEY_LEN]
	ArrayGetString(array,item1,item1str,TRAVTRIE_MAX_KEY_LEN - 1);
	ArrayGetString(array,item2,item2str,TRAVTRIE_MAX_KEY_LEN - 1);

	return strcmp( item1str,item2str );
}

// Rukia: Get a mutable iterator to the travtrie
//	This Handle MUST be closed using CloseHandle, and delete/insert will invalidate iterator
stock travTrieIter:GetTravTrieIterator(TravTrie:trie)
{
	new Array:dp = ArrayCreate();
	ArrayPushCell(dp,_:trie);
	ArrayPushCell(dp,0);
	return travTrieIter:dp;
}

// Rukia: Read the string key that the iterator points to.
//	WILL NOT INCREMENT ITERATOR
stock bool:ReadTravTrieKey(travTrieIter:dp,key[],len)
{
	new Trie:trie = Trie:ArrayGetCell(Array:dp,0);
	
	new Array:iter;
	if(!TrieGetCell(trie,"",_:iter)) return false;
	
	new index = ArrayGetCell(Array:dp,1);
	ArrayGetString(iter,index,key,len);

	return true;
}

stock TravTrieSize(TravTrie:trie)
{
	new Array:iter;
	if(!TravTrieGetCell(trie,"",_:iter)) return false;

	return ArraySize(iter);
}

// Rukia: These functions read from the travtrie via the iterator
//	They WILL INCREMENT THE ITERATOR

stock bool:ReadTravTrieCell(travTrieIter:dp,&any:value)
{
	static tmp[TRAVTRIE_MAX_KEY_LEN];
	new TravTrie:trie = TravTrieIteratorHandler(Array:dp,tmp,TRAVTRIE_MAX_KEY_LEN - 1);
	
	return TravTrieGetCell(trie,tmp,value);
}

stock bool:ReadTravTrieArray(travTrieIter:dp, value[], max_num)
{
	static tmp[TRAVTRIE_MAX_KEY_LEN];
	new TravTrie:trie = TravTrieIteratorHandler(Array:dp,tmp,TRAVTRIE_MAX_KEY_LEN - 1);
	
	return TravTrieGetArray(trie,tmp,value,max_num);
}

stock bool:ReadTravTrieString(travTrieIter:dp, value[], max_num)
{
	static tmp[TRAVTRIE_MAX_KEY_LEN];
	new TravTrie:trie = TravTrieIteratorHandler(Array:dp,tmp,TRAVTRIE_MAX_KEY_LEN - 1);
	
	return TravTrieGetString(trie,tmp,value,max_num);
}

stock TravTrie:TravTrieIteratorHandler(Array:dp,pos[],len)
{
	new Trie:trie = Trie:ArrayGetCell(dp,0);
	
	new Array:iter;
	if(!TrieGetCell(trie,"",any:iter)) return TravTrie:Invalid_Trie;
	
	new index = ArrayGetCell(dp,1);
	ArrayGetString(iter,index,pos,len);
	
	ArraySetCell(dp,1,index + 1);
	
	return TravTrie:trie;
}

// Rukia: Returns true if there is more to read from the iterator

stock bool:MoreTravTrie(travTrieIter:dp)
{
	new Trie:trie = Trie:ArrayGetCell(Array:dp,0);
	
	new Array:iter;
	if(!TrieGetCell(trie,"",any:iter)) return false;
	
	new index = _:ArrayGetCell(Array:dp,1);
	if(ArraySize(iter) <= index) return false;
	
	return true;
}

stock DestroyTravTrieIterator(&travTrieIter:dp)
{
	return ArrayDestroy(Array:dp);
}

stock bool:TravTrieDeleteKeyEx(TravTrie:trie, key)
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);

	return TravTrieDeleteKey(trie,g_Key);
}

//stock TravTrieSize(TravTrie:trie) return TrieGetSize(trie) - 1;

// Hawk: Gets the nth key, starting at 0

stock bool:TravTrieNth(TravTrie:trie, nth, key[], len)
{
	new Array:iter;
	PrepareTravTrie(trie);
	if(!TravTrieGetCell(trie,"",iter)) return false;
	
	new value[TRAVTRIE_MAX_KEY_LEN], result = ArrayGetString(iter,nth,value,TRAVTRIE_MAX_KEY_LEN - 1);
	copy(key,len,value);

	return bool:result;
}

stock bool:TravTrieNthEx(TravTrie:trie,nth,&key)
{
	new bool:result = TravTrieNth(trie,nth,g_Key,TRAVTRIE_MAX_KEY_LEN - 1);
	key = str_to_num(g_Key);
	
	return result;
}

// Hawk: Extended functions for passing an integer as a key

stock bool:TravTrieGetCellEx(TravTrie:trie, key, &any:value)
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);
	new tempvalue, bool:result = TravTrieGetCell(trie,g_Key,tempvalue);
	value = tempvalue;
	return result;
}

stock bool:TravTrieGetStringEx(TravTrie:trie, key, value[], len)
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);
	new bool:result = TravTrieGetString(trie,g_Key,g_Value,TRAVTRIE_MAX_KEY_LEN - 1);
	copy(value,abs(min(len,TRAVTRIE_MAX_KEY_LEN - 1)),g_Value);

	return result;
}

stock bool:TravTrieGetArrayEx(TravTrie:trie, key, any:value[], len)
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);
	new result = TravTrieGetArray(trie,g_Key,g_Value,abs(min(TRAVTRIE_MAX_KEY_LEN,len)));
	for(new count; count < len; count++)
		value[count] = g_Value[count];

	return result;
}

stock bool:TravTrieSetCellEx(TravTrie:trie, key, any:value)
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);
	return TravTrieSetCell(trie,g_Key,value);
}

stock bool:TravTrieSetStringEx(TravTrie:trie, key, const value[])
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);
	return TravTrieSetString(trie,g_Key,value);
}

stock bool:TravTrieSetArrayEx(TravTrie:trie, key, any:value[], len)
{
	formatex(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",key);
	return TravTrieSetArray(trie,g_Key,value,len);
}

/*
#define TravTrieSetCellEx(%1,%2,%3) format(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",%2); TravTrieSetCell(%1,g_Key,%3);
#define TravTrieSetArrayEx(%1,%2,%3,%4) format(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",%2); TravTrieSetArray(%1,g_Key,%3,%4);
#define TravTrieSetStringEx(%1,%2,%3) format(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",%2); TravTrieSetString(%1,g_Key,%3);
#define TravTrieGetCellEx(%1,%2,%3) format(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",%2); TravTrieGetCell(%1,g_Key,%3);
#define TravTrieGetArrayEx(%1,%2,%3,%4) format(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",%2); TravTrieGetArray(%1,g_Key,%3,%4);
#define TravTrieGetStringEx(%1,%2,%3,%4) format(g_Key,TRAVTRIE_MAX_KEY_LEN - 1,"%d",%2); TravTrieGetString(%1,g_Key,%3,%4);
*/

stock bool:ReadTravTrieKeyEx(travTrieIter:dp,&key)
{
	new bool:result = ReadTravTrieKey(dp,g_Key,TRAVTRIE_MAX_KEY_LEN - 1);
	key = str_to_num(g_Key);

	return result;
}
РЕКЛАМИРАЙ ПРИ НАС!
AMXX-BG.INFO
КАК ДА ИЗПОЛЗВАМ
Добави в началото на .sma файла:
#include <celltravtrie>
1. Изтегли
Свали файла от бутона по-горе
2. Копирай
Постави в scripting/include/
3. Включи
Добави #include директивата
4. Компилирай
Използвай amxxpc или scripting/compile.exe
PrivateServ.NET