PDA

Просмотр полной версии : [Вопрос] static string!



X!X
16.07.2018, 22:29
Почему нельзя замутить так?

static const string[] = "SELECT * FROM `accounts` WHERE `name` = '%s' LIMIT 1";
new query[sizeof(string)+Player[playerid][Name]];

выдает варнинги:

error 008: must be a constant expression; assumed zero
error 009: invalid array size (negative, zero or out of bounds)
error 036: empty statement
fatal error 107: too many error messages on one line

А так если вместо Player[playerid][Name] поставить MAX_PLAYER_NAME, то без варнингов компилит

StevenH
16.07.2018, 23:06
Потому что компилятор при компиляции сам рассчитывает размер переменной query. Сколько символов в Player[playerid][Name] компилятор не знает, поэтому и ошибка. Константа MAX_PLAYER_NAME имеет значение 24, поэтому это аналогично вот этому:

new query[sizeof(string)+MAX_PLAYER_NAME];
=
new query[sizeof(string)+24];

X!X
16.07.2018, 23:24
пасибо, закрыто:dash2:

DeimoS
17.07.2018, 07:53
Советую изучить самые основы языка (хотя бы то, что из себя представляют переменные/массивы), ибо то, что ты хотел сделать, не поддаётся какой-либо логике :)

Mavi
18.07.2018, 12:36
Потому что в Pawn'e отсутствуют динамические массивы.

Для будущего: В версиях 0.3e ( или не знаю уже ) и выше Kalcor изменил длину ника на 20 символов. Чтобы не тратить лишние ячейки, рекомендую делать так:

#if defined MAX_PLAYER_NAME
#undef MAX_PLAYER_NAME
#endif
#define MAX_PLAYER_NAME 20

DeimoS
18.07.2018, 12:52
Потому что в Pawn'e отсутствуют динамические массивы.

Для будущего: В версиях 0.3e ( или не знаю уже ) и выше Kalcor изменил длину ника на 20 символов. Чтобы не тратить лишние ячейки, рекомендую делать так:

#if defined MAX_PLAYER_NAME
#undef MAX_PLAYER_NAME
#else
#define MAX_PLAYER_NAME 20
#endif

Эмм, ты, видимо, хотел сделать так:
#if defined MAX_PLAYER_NAME
#undef MAX_PLAYER_NAME
#endif
#define MAX_PLAYER_NAME 20

Хотя для этого лучше создавать отдельный макрос, если в моде реализована система тегов, так как в игре ник действительно может быть до 24-ех символов (это сделано как раз для того, чтоб можно было различные теги добавлять даже тем игрокам, у кого ник 20 символов)

Mavi
18.07.2018, 13:08
Эмм, ты, видимо, хотел сделать так:
#if defined MAX_PLAYER_NAME
#undef MAX_PLAYER_NAME
#endif
#define MAX_PLAYER_NAME 20

Хотя для этого лучше создавать отдельный макрос, если в моде реализована система тегов, так как в игре ник действительно может быть до 24-ех символов (это сделано как раз для того, чтоб можно было различные теги добавлять даже тем игрокам, у кого ник 20 символов)

Ой, да. Исправил, моя ошибка.
Для тега лучше создавать отдельный макрос, потому что MAX_PLAYER_NAME больше 80% скриптеров используют как длина основного ника, без тега ( ну чтобы делать запросы к БД, сравнивать ник со строками и так далее ). Ну если ты конечно не сохраняешь тег и ник в 1 массиве.

DeimoS
18.07.2018, 15:37
Ой, да. Исправил, моя ошибка.
Для тега лучше создавать отдельный макрос, потому что MAX_PLAYER_NAME больше 80% скриптеров используют как длина основного ника, без тега ( ну чтобы делать запросы к БД, сравнивать ник со строками и так далее ). Ну если ты конечно не сохраняешь тег и ник в 1 массиве.

Эмм, то есть, ты предлагаешь стандартному макросу переделать значение на 20, а для 24-ех создать новый макрос?
Это нелогично, как минимум, потому, что ты придёшь к тому же результату, только добавишь одно лишнее действие. Да ещё и код запутаешь, ибо если человек не будет знать, что ты переназначил макрос, то продолжит использовать его как раньше и будет ждать, что он хранит значение "24".

Mavi
18.07.2018, 21:55
Эмм, то есть, ты предлагаешь стандартному макросу переделать значение на 20, а для 24-ех создать новый макрос?
Это нелогично, как минимум, потому, что ты придёшь к тому же результату, только добавишь одно лишнее действие. Да ещё и код запутаешь, ибо если человек не будет знать, что ты переназначил макрос, то продолжит использовать его как раньше и будет ждать, что он хранит значение "24".

#define MAX_PLAYER_NAME (24)
#define MAX_PLAYER_TAG (4)

enum pInfo
{
PlayerNameArray[MAX_PLAYER_NAME],
PlayerTagArray[MAX_PLAYER_TAG]
}
new PlayerInfo[MAX_PLAYERS][pInfo];
new query[45 + MAX_PLAYER_NAME + MAX_PLAYER_TAG];
format(query, sizeof(query), "SELECT 1 FROM `accounts` WHERE `Name` = '%s' AND `Tag` = '%s'", PlayerInfo[playerid][PlayerNameArray], PlayerInfo[playerid][PlayerTagArray]);
mysql_tquery (handle, query, "", "", playerid);

#define MAX_PLAYER_NAME (20)
#define MAX_PLAYER_TAG (4)

enum pInfo
{
PlayerNameArray[MAX_PLAYER_NAME],
PlayerTagArray[MAX_PLAYER_TAG]
}
new PlayerInfo[MAX_PLAYERS][pInfo];
new query[45 + MAX_PLAYER_NAME + MAX_PLAYER_TAG];
format(query, sizeof(query), "SELECT 1 FROM `accounts` WHERE `Name` = '%s' AND `Tag` = '%s'", PlayerInfo[playerid][PlayerNameArray], PlayerInfo[playerid][PlayerTagArray]);
mysql_tquery (handle, query, "", "", playerid);

Констант MAX_PLAYER_TAG все равно используется независимо от значении MAX_PLAYER_NAME. На первом примере можно да не использовать MAX_TAG_NAME, но если с запроса уберем AND `Tag`, там останутся пустые 4 ячейки.
Но другой способ тоже имеется ( new query[41 + MAX_PLAYER_NAME]; / new query[45 + MAX_PLAYER_NAME - 4]; )
Тут не поспоришь, ты тоже прав по сути)

DeimoS
19.07.2018, 13:53
Эмм, я не предлагаю держать макрос со значением 4. Я предлагаю создать макрос со значением 20 и использовать его там, где 100% ник игрока не будет содержать тег (а если на сервере нет систем, которые изменяют ник через SetPlayerName, то и ник никогда не сможет быть больше 20 символов). То бишь, чтоб было два макроса: стандартный, на 24 символа, и наш, на 20 символов.

Хотя на самом деле в этом нет особого смысла. Экономия 4-ех ячеек не скажется на работе сервера положительным образом. Точнее, это никак не проявится для игроков или даже на тестах. А вот проблем из-за этого можно набраться, если наставить макрос с 20-ю символами там, где этого не должно быть. Поэтому использовать подобную оптимизацию нужно сугубо с умом, понимая что вы делаете. Иначе лучше пожертвовать 4-мя ячейками, которые не сильно навредят вашему серверу