PHP: различия между версиями
Oleg4280 (обсуждение | вклад) м Откат правок 46.149.226.42 (обс.) к версии Oleg3280 |
|||
Строка 966: | Строка 966: | ||
</source> |
</source> |
||
=====''Пароли не |
====='''Пароли не совпали'''===== |
||
<source lang=php> |
<source lang=php> |
||
if($_COOKIE['user_login'] == "no_enter" And $_COOKIE['user_enter'] == false){ |
if($_COOKIE['user_login'] == "no_enter" And $_COOKIE['user_enter'] == false){ |
Версия от 12:18, 20 апреля 2015
PHP (произносится пи-эйч-пи́) — скриптовый язык программирования, созданный для генерации HTML-страниц на веб-сервере и работы с базами данных. На сегодняшний момент поддерживается подавляющим большинством представителей хостингов. Входит в LAMP — «стандартный» набор для создания вебсайтов.
Комментарии
PHP предоставляет несколько методов для вставки комментариев. Проще всего пользоваться двойной косой чертой (//), после чего PHP машина игнорирует всё, что расположено до конца строки. Также можно пользоваться многострочными комментариями в стиле С (/*…*/). Для однострочных комментариев можно еще пользоваться символом решетки (#) (комментарий сценарных языков UNIX).
<?php
print '<p>Hello</p>'; //Комментарий
print '<p>Hello</p>'; #Комментарий
/*Комментарий
... и это тоже комментарии
*/
//Комментарии очень удобны в тех случаях, когда необходимо исключить часть кода для отладки программы, например:
$uname = $_POST['uname'];
//$uname = preg_replace('#[^a-zA-Z0-9\_\-\.]#', '', $uname);
//Закомментировали часть кода так как, не выводится желаемого результата, возможно дело в этой строке:
echo $uname;
#Изначально комментарии создавались для того, чтобы не нарушая работы программы, добавить описание к той или иной строке, например:
echo getUsersOnline(2, 1, 4);
/*Аргументы функции:
0 - номер открытого соединения с базой данных;
1 - режим ответа (0 - массив/1 строка);
2 - кол-во минут прошедших с момента последней активности пользователя (необязательный)
*/
?>
Следует помнить о том, что стили комментариев PHP действуют только внутри ограничителей PHP. Если PHP встретит эти символы комментариев вне ограничителей, то они, как и любой текст, будут помещены на HTML-страницу. Например:
<?php
print '<p>Hello</p>'; //Нормальный комментарий.
?>
//А вот этот комментарий отобразится браузером.
<!-- Комментарий HTML. Будет виден в исходном коде HTML, но не в браузере -->
Переменные
В РНР переменные начинаются со знака доллара ($). За этим знаком может следовать любое количество буквенно-цифровых символов и символов подчеркивания, но первый символ не может быть цифрой. Следует также помнить, что имена переменных в РНР чувствительны к регистру, в отличие от ключевых слов.
При объявлении переменных в РНР не требуется явно указывать тип переменной, при этом одна и та же переменная может иметь на протяжении программы разные типы.
Переменная инициализируется в момент присваивания ей значения и существует до тех пор, пока выполняется программа (в случае web-страницы — до тех пор, пока не завершен запрос), или она не будет удалена функцией unset()
.
Функции вывода
В PHP существует несколько способов вывести что-либо в веб страницу:
- Операторы
echo
иprint
- Работают одним и тем же образом, но print всегда возвращает 1, в то время как echo ничего не возвращает. Выводят значение аргумента.
- Функция
print_r()
- Позволяет корректно выводить массивы
- Функция
var_dump()
- Выводит переменную вместе с типом. Очень удобный инструмент для отладки
Вывод различных функций
Аргумент | echo
|
print_r()
|
var_dump()
|
---|---|---|---|
1
|
1
|
1
|
int(1)
|
1.1
|
1.1
|
1.1
|
float(1.1)
|
false
|
bool(false)
| ||
array( 1, 2, 3 )
|
Array
|
Array
|
array(3) {
|
"Test"
|
Test
|
Test
|
string(4) "Test"
|
Типы данных в РНР
Как уже было сказано, PHP предоставляет определенную гибкость в отношении типов переменных, то есть с одной и той же переменной на протяжении программы можно работать и как со строкой, и как с числом. Однако, несмотря на это в РНР существуют набор основных типов данных, которые могут явно указываться при работе с переменными:
- integer (целые числа);
- string (строки);
- boolean (двоичные данные (Истина или Ложь));
- double, если после точки 1 или 2 цифры, float, если больше (числа с плавающей точкой);
- array (массивы);
- object (Объекты);
- NULL (пустой тип);
- Resource (ресурсы);
Есть функция gettype()
, возвращающая тип, который РНР назначил переменной:
<?php
$var1 = '5';
$var2 = 5;
echo gettype($var1) . '<br>' . gettype($var2);
?>
В первом случае РНР вернет string
, во втором integer
.
Стоит заметить, что операция «.» (точка) используется для склеивания (конкатенации) строк.
Существует также функция settype(), которая явно устанавливает тип:
<?php
$var = '5';
echo gettype($var);
settype($var, 'integer');
echo '<br />' . gettype($var);
?>
Выполнение этого фрагмента кода приведет к такому же результату, как и предыдущего.
Кроме функции settype()
преобразование типов в РНР можно осуществлять при помощи операторов преобразования типов. Преобразование типов осуществляется путем указания перед переменной ее нового типа, взятого в скобки:
$var = (integer)$var;
Соответственно, выполнение следующего кода приведет к тому, что РНР вернет integer:
<?php
$var = '5'; //Тип string
$var = (integer)$var; //Преобразуем в int
echo gettype($var);
?>
Внешние переменные
После того, как запрос клиента проанализирован веб-сервером и передан РНР-интерпретатору, последний устанавливает ряд переменных, которые содержат данные, относящиеся к запросу и доступны все время его выполнения.
Сначала PHP инициализирует массивы $_ENV
(переменные окружения) и $_SERVER
[1]. Ассоциативный массив $_SERVER содержит следующие ключи (индексы массива):
$_SERVER['HTTP_USER_AGENT']
— браузер клиента;$_SERVER['HTTP_ACCEPT']
— принимаемые MIME-типы. Может служить для определения возможностей браузера;$_SERVER['PHP_SELF']
— путь к файлу, содержащему выполняющийся скрипт, относительно корневого каталога (папки) сервера. Пример:/w/index.php
Затем РНР заполняет переменную $_GET[]
, являющуюся ассоциативным массивом, которая создаётся при анализе строки запроса. Строка запроса хранится в элементе массива $_SERVER['QUERY_STRING']
и представляет собой информацию, следующую за символом «?» в запрошенном URL. РНР разбивает строку запроса по символам «&»[2] на отдельные элементы, а затем ищет в каждом из этих элементов знак «=». Если знак «=» найден, то создается переменная с именем из символов, стоящих слева от знака равенства. Рассмотрим следующую форму:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>
Введите данные.
</title>
</head>
<body>
<form action="http://localhost/PHP/test.php" method="get">
<p>
HDD:
</p>
<input type="text" name="HDD" />
<br />
<p>
CDROM:
</p>
<input type="text" name="CDROM" />
<br />
<input type="submit" value="Отправить" />
</form>
</body>
</html>
Если Вы в этой форме в строке HDD наберете, к примеру, «Maxtor», а в строке CDROM «Nec», то она сгенерирует следующую форму запроса:
http://localhost/PHP/test.php?HDD=Maxtor&CDROM=Nec
В нашем случае РНР создаст следующие элементы массива с соответствующими индексами (ключами): $_GET['HDD'] = 'Maxtor'
и $_GET['CDROM'] = 'Nec'
.
Вы можете работать с этими переменными из Вашего скрипта (у нас — test.php) как с обычными переменными. В нашем случае они просто выводятся на экран:
<?php
echo "<p>HDD is " . $_GET['HDD'] . "</p>";
echo "<p>CDROM is " . $_GET['CDROM'] . "</p>";
?>
Если запрос страницы выполняется при помощи метода POST
, то появляется группа POST-переменных, которые интерпретируются так же и помещаются в массив $_POST[]
.
Константы
Константы объявляются в РНР при помощи функции define()
:
define('CONSTANT', value)
Первый параметр этой функции — имя константы, второй — её значение. При использовании константы на неё ссылаются по имени:
<?php
define('CONSTANT1', 15);
define('CONSTANT2', "\x20"); //Шестнадцатеричный код символа пробела
define('CONSTANT3', 'Hello');
echo CONSTANT1;
echo CONSTANT2;
echo CONSTANT3;
?>
По традиции имена констант пишут буквами верхнего регистра. И хотя это только традиция, мы Вам рекомендуем ей следовать, поскольку плохие программисты получаются в том числе и из тех, кто не следовал хорошим традициям. Существует функция defined()
, которая проверяет, определена ли константа:
<?php
define('CONSTANT', 'Hello');
if(defined('CONSTANT')) echo '<p>CONSTANT is defined</p>';
?>
Операторы
Математические операторы
В PHP, как и в любом другом языке программирования, есть базовый набор математических операторов:
- Унарный минус (
-
) — изменяет знак числа - Сложение, вычитание, умножение (
+
,-
,*
) — действуют также как и в обычной математике - Деление (
/
) всегда возвращает вещественное число (т.е. с типом данныхfloat
), вне зависимости от результата. - Деление по модулю (
%
) — возвращает остаток от деления
Инкремент и декремент
$a++
— возвращает старое значение $a и увеличивает $a на 1.++$a
— увеличивает $a на 1 и возвращает новое значение $a.$a--
— возвращает старое значение $a и уменьшает $a на 1.--$a
— уменьшает $a на 1 и возвращает новое значение $a.
Операторы сравнения
Существуют следующие операторы сравнения:
$a == $b («равно»)
|
Возвращает true , если $a равно $b
|
$a === $b («идентично»)
|
Возвращает true , если $a равно $b и они имеют один и тот же тип
|
$a != $b или $a <> $b («не равно»)
|
Возвращаетtrue , если $a не равно $b
|
$a > $b («больше»)
|
Возвращает true , если $a больше $b
|
$a < $b («меньше»)
|
Возвращает true , если $a меньше $b
|
$a >= $b («больше или равно»)
|
Возвращает true если $a больше или равно $b
|
$a <= $b («меньше или равно»)
|
true если $a меньше или равно $b
|
Операторы присвоения
Для присвоения переменной нового значения используется оператор «=
»:
$a = $b + $c - 127;
Также существуют сокращённые операторы присвоения(+=
, -=
, .=
, /=
, *=
, %=
):
$a = $a + 1;
#равносильно
$a += 1;
Поразрядные операторы
Эта группа операторов работает с битовыми представлениями значений целочисленных операндов. В основном эти операторы применяются для создания набора булевых флагов.
& |
Поразрядная конъюнкция (AND) |
| |
Поразрядная дизъюнкция (OR) |
^ |
Поразрядное исключающее ИЛИ (XOR) |
~ |
Поразрядное отрицание (NOT) |
<< |
Сдвиг влево битового представления значения левого целочисленного операнда на количество разрядов, равное значению правого целочисленного операнда. |
>> |
Сдвиг вправо битового представления значения левого целочисленного операнда на количество разрядов, равное значению правого целочисленного операнда. |
<?php
echo (4<<2); //16
echo "<br />";
echo (5>>1); //2
echo "<br />";
echo (6&5); //4
echo "<br />";
echo (6|5); //7
echo "<br />";
echo (6^5); //3
?>
if…elseif…else
Оператор if
позволяет выполнять определённый код только при выполнении определённого условия:
<?php
$a = 1;
$b = null;
$c = 2 * 3;
$d = true;
if($a) echo "if(\$a);<br />";
if($b) echo "if(\$b);<br />";
if($c) echo "if(\$c);<br />";
if(!$d) echo "if(!\$d);<br />";
if($a < $c) echo "\$a < \$c;<br />";
?>
Этот код выводит следующие строки:
if($a); if($c); $a < $c;
Для того, чтобы выполнять код только если условие не выполнилось, можно использовать блок else
:
<?php
if(isset($_GET['test'])) echo 'Query contains "test" parameter';
else echo 'Query doesn\'t contain "test" parameter';
?>
Можно использовать инструкцию elseif
(иначе, если):
<?php
if($_GET['test'] == "foo") echo 'test = "foo"';
elseif(isset( $_GET['test']) echo 'Query contains "test" parameter, but it isn\'t "foo"';
else echo 'Query doesn\'t contain "test" parameter';
?>
Переключатель switch
<?php
$a = "A";
switch($a)
{
case 'A':
echo 'Переменная имеет значение "А"';
break;
case 'B':
echo 'Переменная имеет значение "B"';
break;
default: echo 'Ответ не найден';
}
?>
Данный пример выведет «Переменная имеет значение „A“». И этот пример аналогичен:
<?php
$a = "A";
if($a == "A") echo "Переменная имеет значение \"A\"";
elseif($a == "B") echo "Переменная имеет значение \"B\"";
else echo "Ответ не найден";
?>
Операторы цикла
Операторы цикла задают многократное исполнение операторов в теле цикла. В PHP определены 4 разных оператора цикла:
- цикл с предусловием:
while(condition) { statements; }
- цикл с постусловием:
do { statements; } while(condition);
- итерационный цикл:
for(expression1; expression2; expression3) { statements; }
- итерационный цикл foreach (т.е. перебор элементов массива):
foreach(array as [$key =>] $value) { statements; }
Если 3 первых оператора цикла берут свое начало от С-подобных языков, то последний оператор позаимствован у языка Perl.
while
Оператор while
называется оператором цикла с предусловием. При входе в цикл вычисляется выражение условия, и, если его значение отлично от нуля, выполняется тело цикла. Затем вычисления выражения условия и операторов тела цикла выполняется до тех пор, пока значение выражения условия не станет равным нулю. Оператором while
удобно пользоваться для просмотра всевозможных последовательностей, если в конце них находится заранее известный символ. (Это очень удобно в C++, к примеру для определения длины строки, поскольку в С++, по определению, строка есть последовательность символов типа char, заканчивающаяся нулевым символом).
Пример простейшего цикла while:
<?php
$var = 5;
$i = 0;
while(++$i <= $var) echo $i . '<br />';
?>
Этот код выдает в окне браузера цифры от одного до пяти.
Для выхода из цикла применяется оператор break
. При обнаружении этого оператора текущая итерация цикла прекращается, и последующие итерации не происходят. При выполнении следующего примера, несмотря на то, что переменная $var = 7
, в окне браузера появятся цифры от 1 до 5.
<?php
$var = 7;
$i = 0;
while(++$i <= $var)
{
echo $i . '<br />';
if($i == 5) break;
}
?>
Иногда бывает нужно прервать только текущую итерацию, и перейти сразу к следующей. Для этого применяется оператор continue
:
<?php
$var = 7;
$i = 0;
while (++$i <= $var)
{
if($i == 5) continue;
echo $i . '<br />';
}
?>
В этом примере выводятся цифры от 1 до 7, кроме цифры 5.
Заметим, что если вы поставите условный оператор после операторов echo
, код будет ошибочным, и выведутся все цифры от 1 до 7, поскольку проверка условия выхода из цикла на данной итерации, будет происходить уже после выполнения этой итерации.
Бесконечный цикл реализуется при помощи оператора while следующим образом:
while(true)
{
...
}
Примечание: В PHP стандартное время исполнения скрипта — 30 секунд (эту настройку можно изменить в файле php.ini). То есть по прошествии 30 секунд с начала выполнения скрипта, его действие будет прервано. Таким образом, время выполнения бесконечного цикла — полминуты.
do…while
Этот оператор называется оператором цикла с постусловием. При входе в цикл в любом случае выполняется тело цикла (то есть цикл всегда будет выполнен хотя бы один раз), затем вычисляется условие, и если оно не равно 0, вновь выполняется тело цикла. В нижеследующем примере нуль всегда будет добавлен в список, независимо от условия (++$i <= $var)
:
<?php
$var = 5;
$i = 0;
do
{
echo $i . '<br />';
}
while(++$i <= $var);
?>
Результат:
0<br />1<br />2<br />3<br />4<br />5<br />
Цикл с постусловием бывает полезен при обработке некоторых последовательностей, когда обработку нужно заканчивать не до, а после появления концевого признака.
Бесконечный цикл реализуется так:
do
{
...
}
while(true);
for
Как уже говорилось, итерационный цикл имеет следующий формат:
for(expression1; expression2; expression3) {
statements;
}
Здесь expression1
(инициализация цикла) — последовательность определений и выражений, разделяемая запятыми. Все выражения, входящие в инициализацию, вычисляются только один раз при входе в цикл. Как правило, здесь устанавливаются начальные значения счетчиков и параметров цикла. Смысл выражения-условия expression2
такой же как и у циклов с предусловиями. При отсутствии выражения-условия предполагается, что его значение всегда истинно. Выражения expression3
вычисляются в конце каждой итерации после выполнения тела цикла.
В следующем скрипте, мы по традиции выведем числа от 0 до 5:
<?php
$var = 5;
for($i = 0; $i <= $var; $i++)
{
echo $i . '<br />';
}
?>
Результат аналогичен, показанному на предыдущем рисунке.
foreach
Оператор цикла foreach
предназначен для работы с элементами массива. Следующий код превратит все элементы массива в единицы.
<?php
$arr = array(1, 2, 3, 4);
$i = 0;
foreach ($arr as &$a)
{
$a -= $i++;
}
?>
Также предусмотрена возможность работы с ассоциативными массивами. При обработке следующего кода в переменной $name
будет храниться ассоциативный индекс элемента, а в переменной $value
— его значение. Проще говоря, ($arr[$name] == $value)
.
<?php
...
foreach ($arr as $name => $value) {
//тело цикла
}
?>
Тернарный оператор «?» :
Тернарный оператор «?:» это вид условного оператора, он проверяет Выражение 1 и если оно верно, то присваивает значение Выражения 2, иначе — Выражения 3.
<?php
$a = true;
$b = false;
$c = 11;
$d = 10;
$f = $a ? $c : $d; // Переменной $f присвоится значение переменной $c, т. к. значение выражения $a истинно
$g = $b ? $c : $d; // Здесь наоборот - $g будет присвоено значение $d
$h = (!empty($n)) ? $n : $c+$d; // Сперва проверится существование переменной $n, а т. к. она не существует, переменной $h присвоится сумма $c и $d, т. е. 21
?>
Строковые функции PHP
Несмотря на то, что эта глава написана скорее в духе справочника, материал, изложенный в ней, достаточно серьезен, хотя и не самый сложный для понимания. Умение грамотно работать со строками очень важно для программиста. Строковых функций в PHP немало, причем многие из них, так или иначе, просто дублируют друг друга. Однако, приемы работы с основными блоками функций (функции поиска и замены в тексте, функции удаления пробельных символом (trim-функции), функции форматного вывода) надо представлять очень четко.
Вообще говоря, по определению, строка — это последовательность символов типа char, которая заканчивается нулевым символом. Поэтому, можно, конечно, радоваться тому, что при работе со строками, нам не приходится жонглировать указателями в стиле C/C++, однако не стоит забывать о том, что цена этому удобству — быстродействие. Поэтому некоторые приводимые здесь функции мы будем обсуждать в том числе и с точки зрения их быстродействия.
Функция htmlspecialchars
string htmlspecialchars(string $str)
Эта функция преобразовывает некоторые специальные символы HTML в другой формат. При этом они будут отображаться без учета их специального назначения.
Пример
корректное формирование и вывод гиперссылки, содержащей определённые параметры:
$link_search_subject = "Экранирование";
$link_label = "Поиск по слову " . "$link_search_subject";
echo
'<a href=' . htmlspecialchars("http://ru.wikibooks.org/wiki/Служебная:Search?search=".urlencode($link_search_subject)
."&go=".urlencode("Перейти")).'">'.htmlspecialchars($link_label).
'</a>';
заметьте, что следующий (ниже представленный) код, содержит грубое нарушение, так как формирует гиперссылку с атрибутом содержащим незаконченную (не закрытую) ссылку на сущность (&…;) :
$link_search_subject = "Экранирование";
echo
'<a href="http://ru.wikibooks.org/wiki/Служебная:Search?search='.urlencode($link_search_subject)
.'&go='.urlencode("Перейти").'">'. // НАРУШЕНИЕ!!
"Поиск по слову Экранирование".
'</a>';
это довольно часто встречаемая ошибка.
Функции поиска в тексте
substr()
Функция substr()
возвращает часть строки.
Например:
echo substr('Simple text', 3, 7);
Где 3 — точка отсчета, а 7 — длина изымаемой строки. Если же требуется вести отсчет от конца строки, используйте отрицательное значение.
Пример
Эта функция разобьет число по трём разрядам:
<?php
function my_int($value)
{
$len = strlen($value);
if ($len <= 3) return $value;
else return my_int(substr($value, 0, $len-3)) . ' ' . substr($value, $len-3, 3);
}
}
echo my_int(12345678); //=> 12 345 678
Для работы с разными кодировками используется функция:
string mb_substr ( string $str , int $start [, int $length [, string $encoding ]] )
strpos()
int strpos (string haystack, string needle [, int offset])
Возвращает позицию первого вхождения подстроки needle
(в переводе с английского — «иголка») в строку haystack
(в переводе с английского, как вы уже догадались, — «стог сена»). Необязательный аргумент offset
позволяет указать, с какого по счету символа строки haystack
начинать поиск.
Если подстрока needle
не найдена, strpos()
возвращает FALSE
.
Пример:
Эта функция определяет модель браузера:
<?php
function get_current_browser() {
$browser = strtoupper($_SERVER['HTTP_USER_AGENT']);
if(strpos($browser, 'MSIE') !== false) $browser = 'Internet Explorer';
elseif(strpos($browser, 'FIREFOX') !== false) $browser = 'Firefox';
elseif(strpos($browser, 'KONQUEROR') !== false) $browser = 'Konqueror';
elseif(strpos($browser, 'LYNX') !== false) $browser = 'Lynx'; }
else { $browser = $_SERVER['HTTP_USER_AGENT'];
return $browser;
}
get_current_browser();
?>
strrpos()
Возвращает позицию последнего вхождения символа
int strrpos (string haystack, string needle [, int offset])
Возвращает позицию последнего вхождения needle
в строку haystack
. В PHP 4 используется только первый символ строки needle
.
Начиная с PHP 5 необязательный аргумент offset
позволяет указать, с какого по счету символа строки haystack
начинать поиск. Отрицательное значение предписывает прекратить поиск при достижении определенной позиции до конца строки.
Если подстрока needle
не найдена, возвращает FALSE
.
Пример:
Эта функция достаёт из URL имя файла (только пример, в жизни можно использовать функцию basename()
):
function getfname($url)
{
$pos = strrpos($url, '/', 8); // начиная с 8 символа, т.к. в "http://" искать не нужно
$filename = '';
if ($pos === false) {
// Ошибка, url задан неверно.
return false;
} else {
$filename = substr($url, $pos + 1);
}
return $filename;
}
strstr(), stristr()
string strstr (string $haystack, string $needle [, bool $before_needle = false ])
Возвращает подстроку строки haystack
начиная с первого вхождения подстроки needle
до конца строки. Функция stristr()
выполняет ту же функцию, но не чувствительна к регистру.
Пример:
<?php
$text = 'www.wikibooks.org';
$strstr = strstr($text, '.');
print $strstr;
?>
Данный пример выведет «.wikibooks.org».
Для работы с разными кодировками используются функции:
string mb_strstr (string $haystack , string $needle [, bool $before_needle = false [, string $encoding ]])
string mb_stristr (string $haystack , string $needle [, bool $before_needle = false [, string $encoding ]])
где параметр encoding
- название используемой кодировки символов (например UTF-8). Если этот параметр опущен, используется внутренняя кодировка.
strchr()
Эта функция является псевдонимом функции strstr()
.
strrchr()
string strrchr (string $haystack, char $needle)
Возвращает подстроку строки haystack
начиная с последнего вхождения needle
до конца строки.
Если подстрока needle
не найдена, возвращает FALSE
.
Если needle
состоит более чем из одного символа, используется только первый символ.
Если needle
не является строкой, он приводится к целому и трактуется как код символа.
Пример:
<?php
$text = 'www.wikibooks.org';
$strrchr = strrchr($text, '.');
print $strrchr;
?>
Данный пример выведет «.org».
substr_count()
int substr_count (string $haystack, string $needle)
Возвращает число вхождений подстроки needle
в строку haystack
.
Можно использовать или текст в кавычках (или апострофах) или переменные.
Пример:
<?php
print substr_count('www.wikibooks.org', 'o');
?>
Данный пример выведет «3».
strspn()
strspn - находит длину начального сегмента маски.
int strspn (string $str1, string $str2)
Возвращает длину начального сегмента str1, состоящего полностью из символов строки str2.
Пример:
<?
$var = strspn("42 is the answer, what is the question ...", "1234567890");
?>
присваивает 2 переменной $var, поскольку строка "42" будет самым длинным сегментом, содержащим символы из "1234567890".
strcspn()
Обратная функции strspn() Функция strcspn() Определяет отсутствие начальных символов в строке.
Функция strcspn() возвращает длину начального фрагмента строки str1, состоящего полностью не из символов, которые есть в строке str2.
Система пользователей
Алгоритмы системы пользователей — В этой статье будет описаны алгоритмы системы пользователей и их коды на языке PHP.
Регистрация
Алгоритм регистрации пожалуй самый простой из тех, что мы будем здесь использовать. Серверу просто предстоит запись введённые пользователем данные и записать результата хэш-функции от пароля.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>
Регистрация
</title>
</head>
<body>
<?php
//register
//Подключение к MySQL
mysql_connect("localhost", "root", "") or die(mysql_error);
//Подключение к базе данных deskside
mysql_select_db("deskside") or die(mysql_error);
$find_id_sql = mysql_query("SELECT * FROM users ORDER BY id ASC");
$find_id_row = mysql_num_rows($find_id_sql);
$find_names = mysql_query("SELECT * FROM users WHERE login='".$_POST['login']."'");
$find_row = mysql_num_rows($find_names);
$id_counter = 1;
//Вычисление последнего ID
while ($find_id_row = mysql_fetch_assoc($find_id_sql)){
$id_counter += 1
}
$user_already = false; //Проверка, есть ли уже такой пользователь
if ($_POST['register'])
{
while($find_row == mysql_fetch_assoc($find_names))
{
//Проверка, есть ли уже такой пользователь
if ($find_row['login'] == $_POST['login']){
$user_already = true; //Если есть, то так и пишем
}
}
if($user_already){
echo "
<p>
Такой пользователь уже есть <br /> <a href=\"http://localhost/register.htm">Пройти регистрацию заново... </a>
</p>
";
}
else
{
//Если такого пользователя всё-таки нет, то регистрируем нового пользователя с таким именем
if ($_POST['password'] == $_POST['second_password'])
{
//Проверка совпадений паролей
//Совпали:
echo "Регистрация проведена успешно";
$md5_password = md5($_POST['password']); //Хэширование пароля для базы данных
mysql_query("INSERT INTO users (`id`, `login`, `password`, `e-mail`, `name`) VALUES ('".$id_counter."', '".$_POST['login']."', '".$md5_password."', '".$_POST['e-mail']."', '".$_POST['name']."')");
}
else
{
echo "
<p>
Ошибка регистрации. Возможно, пароли не совпадают! <br /> <a href=\"http://localhost/register.htm\">Пройти регистрацию заново</a>
</p>
";
}
}
}
if($_POST['register'])
{
//Если пользователь уже нажал кнопку РЕГИСТРАЦИЯ, то зачем ему заново показывать форму?!
}
else
{
//Если он уже кликнул, то мы не показываем форму, а выводим либо сообщение о подтверждении, либо об ошибке
echo '
<form method=\"post\">
<p>
Логин: <input type=\"text\" name=\"login\" />
</p>
<p>
Пароль: <input type=\"password\" name=\"password\">
</p>
<p>
Пароль еще раз: <input type=\"password\" name=\"second_password\" />
</p>
<p>
E-mail: <input type=\"email\" name=\"e-mail\" />
</p>
<p>
Ваше имя: <input type=\"text\" name=\"name\" />
</p>
<input type=\"submit\" name=\"register\" value=\"Зарегестрироваться\">
</form>
';
}
?>
</body>
</html>
Авторизация пользователя
Вход пользователя будет производиться по следующему алгоритму:
- Пользователь заполняет форму: Логин, Пароль.
- Данные запоминаются в переменной $_POST, после чего будут обрабатываться на сессии[3].
- Уже в сессии хэшируется введенный пользователем пароль алгоритмом MD5.
- Подключение к базе данных SQL и импорт данных со строки пользователя (Допустим, пользователь ввел имя пользователя admin) admin, затем запись всей строки в массив $table - такой вариант поможет сократить много нервов и строк.
- Сравнение зашифрованного пароля, который в базе данных с зашифрованным, введенным пользователем.
- Если пароли совпадают, записываются COOKIE с информацией о авторизации пользователя. ("user_enter" & "user_login").
- Закрытие сессии методом перенаправления на другую страницу. - header (Location: ...);
Форма входа
<?php
session_start();
#Этот шаблон можно вставлять в любую часть сайта, он будет работать в любом случае.
?>
<form action="session.php" method="POST">
<p>
Логин: <input type="text" name="login" />
</p>
<p>
Пароль: <input type="password" name="password" />
</p>
<input type="submit" value="Вход" />
</form>
Сессия (session.php)
<?php
//Заметьте, нету команд echo - эту команду можно использовать только после того, как отправились все куки
// P.S. Если на странице используются куки, лучше не использовать кодировку UTF-8
session_start();
if ($_POST['exit']){ //Если пользователь кликнул "Выход"
// Чистим куки о его авторизации и логине
unset($_COOKIE['user_enter']);
unset($_COOKIE['user_login']);
}
//Подключение к MySQL
mysql_connect("localhost", "root", "1234") or die(mysql_error); // localhost - стандартный сервер баз данных | root - логин MySQL | 1234 - Пароль для пользователя MySQL
//Подключение к базе данных
mysql_select_db("base") or die(mysql_error); //base - имя базы данных
$check_password = mysql_query("SELECT * FROM `base`.`users` WHERE (login='".$_POST['login']."')"); // SQL Запрос для проверки пароля
$row_check_password = mysql_num_rows($check_password);
while($row_check_password = mysql_fetch_assoc($check_password)){ //Получение данных о пользователе
$table['id'] = $row_check_password['id']; // ID Пользователя
$table['login'] = $row_check_password['login']; // Логин пользователя
$table['password'] = $row_check_password['password']; //Пароль пользователя в зашифрованном виде
$table['blog_name'] = $row_check_password['blog_name']; //Имя блога пользователя
}
//Проверка паролей
if ($_POST['enter']){
$md5_password = md5($_POST['password']); //хэширование пользовательского пароля
if ($md5_password == $table['password'] && $_POST['login'] == $table['login']){ //Если хэш пароля пользователя и логин совпадают с хэшем пароля и логином из базы данных
//Пользователь вошёл в систему
setcookie("user_enter", true); //кука - пользователь авторизировался
setcookie("user_login", $_POST['login']); //кука - логин пользователя
setcookie("user_blog", $table['blog_name']); //кука - имя блога пользователя
}else{
//Пароль не подтвердился
setcookie("user_login", "no_enter"); // кука - логин пользователя "не вошёл"
setcookie("user_enter", false); // кука - пользователь не вошёл
}
}
header('Location: http://deskside/main.php?page=home'); //Перенаправление на главную страницу
?>
Вывод данных пользователя
Для вывода данных пользователя будут использоваться куки, но поскольку они могут содержать только латинские буквы и цифры, они будут использоваться только как идентификатор имени пользователя и подтверждения его авторизации. Пользователю нужно выводить максимум информации о его ошибках, если ваш проект будет очень большим и пользователь при входе будет вводить не только логин и пароль, а ещё 20 полей, то пользователю будет не очень удобно при опечатке смотреть на такое сообщение: "Возможно вы ошиблись при заполнении данных, попробуйте ещё раз". Ему будет гораздо приятнее, если ему выведут сообщение с возможным полем опечатки и самой опечаткой. Но в нашем варианте будет рассматриваться только вариант с логином и паролем. Естественно невозможно использовать один и тот-же текст для вывода разной информации. Всего их три, если пользователь авторизировался, если пароли не совпадают и если пользователь ещё не авторизировался и хочет ввести свои данные. Проще всего будет просто выводить шаблон на страницу ($login_form)
Пользователь авторизировался
if ($_COOKIE['user_enter']){
$login_form ='
<form method="post">
Вы вошли как <b>'.$login.'</b> <br><br>
<a href="http://deskside/main.php?page=register">Регистрация</a> <br>
<a href="http://deskside/main.php?page=profile">Профиль</a> <br>
<input type="submit" name="exit" value="Выход">
</form>
';
}
Пароли не совпали
if($_COOKIE['user_login'] == "no_enter" And $_COOKIE['user_enter'] == false){
$login_form = '
<form method="post">
Ошибка! Пароль неправильный!
<br>
<hr>
<b><input type="submit" name="exit" value="Ввести снова"></b> <br>
<a href="http://deskside/main.php?page=register">Регистрация</a>
</form>
';
}
Форма авторизации
$login_form = '
<table>
<tr>
<td> </td>
<td> </td>
<td> </td>
</tr>
<tr>
<td> </td>
<td class="style10">
<form action="session.php" method="POST">
Логин: <br>
<input type="text" name="login"> <br>
Пароль: <br>
<input type="password" name="password">
<br>
<hr>
<input type="submit" name="enter" value="Войти">
<br>
<br>
<a href="http://deskside/main.php?page=register">Регистрация</a>
</form>
</td>
<td> </td>
</tr>
<td>
<td> </td>
<td> </td>
<td> </td>
</td>
</table>
';
Примечания
- ↑ На самом деле, порядок инициализации суперглобальных массивов зависит от настроек в файле php.ini
- ↑ Символ разделения также может меняться в файле php.ini. Часто используется символ «;».
- ↑ Приемущество сессий в том, что обычный пользователь даже не заметит, как его перенаправили на другую страницу, а значит будет сложнее взломать PHP код. На странице входа отображается только перенаправление на session.php и форма входа. Если конечно не посмотрит внимательно на HTML код, но это ему ничего не даст, по скольку он не сможет взять из файла session.php сам PHP код
Ссылки
- Руководство по PHP (включая FAQ)
- Documentation
- PHP Manual (оригинал, англ.)
- Самоучитель (учебник) по PHP