IsRPNick - проверка на RP-ник
Функция была сделана давно на основе варианта от frog163, но была изменена для повышения быстродействия и, в конце концов, стала почти не похожа на оригинал.
stock bool:IsRPNick(const name[])
{ // http://pro-pawn.ru/showthread.php?7528
static i, __;
if ('A' <= name[0] <= 'Z' && 'a' <= name[1] <= 'z')
{
for (i = 1, __ = 0;;)
{
switch (name[++i])
{
case 'a'..'z':
continue;
case '_':
if (__++, 'A' <= name[++i] <= 'Z' && 'a' <= name[++i] <= 'z')
continue;
else
break;
case '\0':
return (i >= 4 && __ == 1);
default:
return false;
}
}
}
return false;
}
Также есть улучшенная реализация с использованием оператора emit. Работает в ~1.6 (~2.1 с JIT) раза быстрее обычной реализации, но требует версию компилятора 3.10.5+.
Открыть/закрыть stock bool:IsRPNick(const name[])
{ // http://pro-pawn.ru/showthread.php?7528
static num_underscores, ptr;
emit
{
load.s.pri name
load.i
const.alt 'A'
jsless ret_false
const.alt 'Z'
jsgrtr ret_false
load.s.pri name
add.c (cellbits / charbits)
load.i
const.alt 'a'
jsless ret_false
const.alt 'z'
jsgrtr ret_false
zero num_underscores
load.s.pri name
add.c (cellbits / charbits * 2)
jump loop_entry
loop:
load.pri ptr
add.c (cellbits / charbits)
loop_entry:
stor.pri ptr
load.i
const.alt 'a'
jsless is_underscore
const.alt 'z'
jsleq loop
is_underscore:
const.alt '_'
jneq is_term
inc num_underscores
load.pri ptr
add.c (cellbits / charbits)
load.i
const.alt 'A'
jsless ret_false
const.alt 'Z'
jsgrtr ret_false
load.pri ptr
add.c (cellbits / charbits * 2)
stor.pri ptr
load.i
const.alt 'a'
jsless ret_false
const.alt 'z'
jsleq loop
jump ret_false
is_term:
jnz ret_false
load.pri ptr
load.s.alt name
sub
const.alt (cellbits / charbits * 4)
jsless ret_false
load.pri num_underscores
const.alt 1
eq
retn
ret_false:
}
return false;
}
Пример использования:
{
new name[MAX_PLAYER_NAME+1];
if (!IsRPNick(name))
{
}
return 1;
}
Автор оригинала: frog163
Доработка: Daniel_Cortez