Какой язык вы используете?
Большинство языков имеют функцию или класс Uri Encoder / Decoder. Я бы посоветовал вам сначала декодировать строку, а затем проверять действительные (или недопустимые) символы.
т.е. что-то вроде / [\ w] / (пусто - пробел)
С регулярным выражением в первую очередь вам нужно учтите, что www.example.com/index.html?user=admin&pass=%%250 означает, что проход действительно составляет "% 250".
Отличная головоломка!
Я вижу, что большинство людей запоминают положение каждой части. Как насчет того, чтобы применить более простой подход и сохранить содержимое каждого квадрата ? Это обеспечивает автоматическое продвижение и захваченные фрагменты.
И это позволяет кодирование Хаффмана . Фактически, начальная частота фигур на доске почти идеальна для этого: половина квадратов пусты, половина оставшихся квадратов - пешки и т. Д.
Учитывая частоту каждой фигуры, я построил Хаффмана дерево на бумаге, которое я здесь повторять не буду. Результат, где c
обозначает цвет (белый = 0, черный = 1):
для всей доски в исходной ситуации у нас есть
Всего: 164 бита для начального состояния платы. Значительно меньше, чем 235 бит ответа, получившего наибольшее количество голосов. И он будет только уменьшаться по мере продвижения игры (кроме случаев повышения).
Я смотрел только на положение фигур на доске; дополнительное состояние (чей ход, кто рокировался, на проходе, повторяющиеся ходы и т.д.) нужно будет кодировать отдельно. Может быть, еще 16 бит самое большее, Возможные оптимизации:
c
, которые затем могут быть выводится из квадрата, на котором находится слон. (Пешки, повышенные до слонов, нарушают эту схему ...) ^([^%]|%([013-9a-fA-F][0-9a-fA-F]|2[1-9a-fA-F]))*$
Отклонить строку, если она соответствует % [^ 2] [^ 0]
Я думаю, вы найдете то, что вам нужно
/^([^%]|%%|%20)+$/
Edit : добавлен случай, когда %%
является допустимой строкой внутри URI
Edit2 : и исправлен для случая, когда он должен завершиться неудачно: -)
Edit3 :
Если вам нужно использовать его в редакторе (что объясняет, почему вы не можете использовать более программный способ), тогда вам нужно правильно экранировать все специальные символы, например в Vim это регулярное выражение должно быть lool:
/^\([^%]\|%%\|%20\)\+$/
Возможно, лучший подход - выполнить эту проверку после того, как вы декодируете эту строку:
string name = HttpUtility.UrlDecode(Request.QueryString["Name"]);
Это требует проверки на "плохие" шаблоны. Если мы разрешаем % 20
- нам не нужно проверять его существование.
Как уже говорили другие, %% тоже действителен ... и %% 25
будет % 25
Приведенное ниже регулярное выражение соответствует всему, что не вписывается в приведенные выше правила
/(?<![^%]%)%(?!(20|%))/
Первые скобки проверяют, стоит ли перед символом% (что означает, что это %%
), а также проверяет, что это не %%%
. Затем он проверяет наличие% и проверяет, не соответствует ли элемент после 20
Это означает, что если что-то определено регулярным выражением, вам, вероятно, следует отклонить его.
Я согласен с комментарием Доминика по вопросу. Не используйте Regex.
Если вы хотите избежать сканирования строки дважды, вы можете просто итеративно искать %
, а затем проверить, что за ним следует 20
и ничего еще. ( Обновление: разрешить %
после интерпретировать как буквальную последовательность % nnn
)
// pseudo code
pos = 0
while (pos = mystring.find(pos, '%'))
{
if mystring[pos+1] = "%" then
pos = pos + 2 // ok, this is a literal, skip ahead
else if mystring.substring(pos,2) != "20"
return false; // string is invalid
end if
}
return true;