PHP синтаксический анализ / синтаксические ошибки; и как их решить?

552

Все сталкиваются с синтаксическими ошибками. Даже опытные программисты делают опечатки. Для новичков это всего лишь часть учебного процесса. Однако часто легко интерпретировать сообщения об ошибках, такие как:

Ошибка синтаксического анализа PHP: синтаксическая ошибка, неожиданное '{' в index.php в строке 20

Неожиданный символ не всегда настоящий преступник. Но номер строки дает приблизительное представление о том, с чего начать.

Всегда смотрите на контекст кода. Синтаксическая ошибка часто скрывается в упомянутых или в предыдущих строках кода. Сравните ваш код с примерами синтаксиса из руководства.

Хотя не каждый случай соответствует другому. Тем не менее, есть некоторые общие шаги для решения синтаксических ошибок. Эти ссылки суммировали общие подводные камни:

Тесно связанные ссылки:

А также:

Хотя Qaru также приветствует начинающих программистов, он в основном нацелен на вопросы профессионального программирования.

  • Отвечать на все ошибки в коде и узкие опечатки считается не по теме.
  • Поэтому, пожалуйста, уделите время, чтобы выполнить основные шаги, прежде чем публиковать запросы на исправление синтаксиса.
  • Если вам все еще нужно, пожалуйста, покажите свою собственную инициативу решения, предпринятые исправления и свой мыслительный процесс о том, что выглядит или может быть не так.

Если ваш браузер отображает сообщения об ошибках, такие как "SyntaxError: недопустимый символ", то это на самом деле не -related, а - синтаксическая ошибка.


Синтаксические ошибки, возникающие в коде поставщика. Наконец, учтите, что если синтаксическая ошибка возникла не при редактировании базы кода, а после установки или обновления пакета внешнего поставщика, это может быть связано с несовместимостью версии PHP, поэтому проверьте требования поставщика к настройке платформы.,

  • 0
    Для ответа недостаточно данных, но можно написать анализатор с parsekit_compile_string и добавить более дружественные ответы. Если интегрировано в вашу IDE, это может быть довольно информативным.
  • 3
    Вы вложили внушительный объем работы в это. Уважение к этому. Для учителей, вероятно, очень полезно научиться быстро указывать на ошибки, а также для тех, кто создает IDE или внедряет быстрые исправления. Однако IDE уже эффективно выполнит большую часть этой работы за вас, как предлагает @Panique. Кроме того, во многих случаях хороший старт начинается с нуля.
Показать ещё 14 комментариев
Теги:
debugging
parsing
syntax-error

16 ответов

260
Лучший ответ

Каковы синтаксические ошибки?

PHP относится к С-стилю и императивным языкам программирования. У него есть жесткие правила грамматики, которые он не может восстановить при обнаружении неулокальных символов или идентификаторов. Это не может угадать ваши намерения кодирования.

Изображение 731

Самые важные советы

Есть несколько основных мер предосторожности, которые вы всегда можете предпринять:

  • Используйте правильные отступы кода или используйте любой высокий стиль кодирования. Читаемость предотвращает неровности.

  • Используйте IDE или редактор для PHP с подсветкой синтаксиса. Что также помогает с скобками/балансировкой скобок.

    Изображение 732

  • Прочитайте справочник по языку и примеры в руководстве. Дважды, чтобы стать несколько опытным.

Как интерпретировать ошибки парсера

Типичное сообщение об ошибке синтаксиса гласит:

Ошибка разбора: синтаксическая ошибка, неожиданный T_STRING, ожидающий ' ; ' в file.php в строке 217

Который перечисляет возможное местоположение синтаксической ошибки. Смотрите упомянутое имя файла и номер строки.

Прозвище, такие как T_STRING объясняет, какой символ анализатор/токенизатор не удалось обработать, наконец. Однако это не обязательно является причиной синтаксической ошибки.

Важно также рассмотреть предыдущие строки кода. Часто синтаксические ошибки - это просто неудачи, случившиеся ранее. Номер строки ошибки - именно то, где анализатор окончательно отказался от обработки всего этого.

Решение синтаксических ошибок

Есть много подходов, чтобы сузить и исправить синтаксические ошибки.

  • Откройте указанный исходный файл. Посмотрите на упомянутую строку кода.

    • Для убегающих строк и неулокальных операторов, это обычно, где вы найдете виновника.

    • Прочитайте строку слева направо и представьте, что делает каждый символ.

  • Более регулярно вы должны смотреть и на предыдущие строки.

    • В частности, отсутствует ; точки с запятой отсутствуют в конце предыдущей строки/оператора. (По крайней мере, со стилистической точки зрения.)

    • Если { кодовые блоки } неправильно закрыты или вложены, вам может потребоваться еще больше изучить исходный код. Используйте правильный отступ кода, чтобы упростить это.

  • Посмотрите на цвет синтаксиса !

    • Строки, переменные и константы должны иметь разные цвета.

    • Операторы +-*/. также должен быть отчетливо окрашен. В противном случае они могут быть в неправильном контексте.

    • Если вы видите, что раскрашивание строк распространяется слишком далеко или слишком коротко, значит, вы обнаружили неэкранированный или отсутствующий закрывающий " или ' маркер строки.

    • Наличие двух одинаковых знаков препинания рядом друг с другом также может означать проблемы. Обычно операторы являются одинокими, если это не ++, -- или круглые скобки после оператора. Две строки/идентификаторы, непосредственно следующие друг за другом, являются неверными в большинстве контекстов.

  • Пробел - твой друг. Следуйте любому стилю кодирования.

  • Временно разбить длинные очереди.

    • Вы можете свободно добавлять символы новой строки между операторами или константами и строками. Затем синтаксический анализатор конкретизирует номер строки для анализа ошибок. Вместо того, чтобы смотреть на очень длинный код, вы можете изолировать отсутствующий или неулокальный синтаксический символ.

    • Разделите сложные операторы if на отдельные или вложенные условия if.

    • Вместо длинных математических формул или логических цепочек используйте временные переменные для упрощения кода. (Более читабельно = меньше ошибок.)

    • Добавьте новые строки между:

      1. Код, который вы можете легко определить как правильный,
      2. Части, в которых вы не уверены,
      3. И строки, на которые парсер жалуется.

      Разделение длинных блоков кода действительно помогает определить источник синтаксических ошибок.

  • Закомментируйте оскорбительный код.

    • Если вы не можете изолировать источник проблемы, начните закомментировать (и, следовательно, временно удалить) блоки кода.

    • Как только вы избавились от ошибки синтаксического анализа, вы нашли источник проблемы. Посмотри внимательнее там.

    • Иногда вы хотите временно удалить завершенные функциональные/методические блоки. (В случае непревзойденных фигурных скобок и ошибочно с отступом кода.)

    • Если вы не можете решить проблему с синтаксисом, попробуйте переписать закомментированные разделы с нуля.

  • Как новичок, избегайте некоторых запутанных синтаксических конструкций.

    • Троичный ? : ? : оператор условия может компактировать код и действительно полезен. Но это не помогает удобочитаемости во всех случаях. Предпочитаю простые операторы if пока они не обращены.

    • Альтернативный синтаксис PHP (if:/elseif:/endif;) является общим для шаблонов, но, возможно, менее прост для понимания, чем обычные блоки { code }.

  • Наиболее распространенные ошибки новичка:

    • Пропущенные точки с запятой ; для завершения операторов/строк.

    • Несоответствующие строковые кавычки для " или ' и неэкранированные кавычки внутри.

    • Забытые операторы, в частности для строки . конкатенации.

    • Несбалансированный ( скобки ). Подсчитайте их в сообщенной строке. Есть ли их равное количество?

  • Не забывайте, что решение одной синтаксической проблемы может раскрыть следующую.

    • Если вы решите одну проблему, но в следующем коде появится другая, вы в основном на правильном пути.

    • Если после редактирования новой синтаксической ошибки появляется в той же строке, то ваша попытка изменения была неудачной. (Не всегда, хотя.)

  • Восстановите резервную копию ранее работающего кода, если вы не можете это исправить.

    • Принять систему управления версиями исходного кода. Вы всегда можете посмотреть diff в сломанной и последней рабочей версии. Что может быть полезным для понимания проблемы синтаксиса.
  • Невидимые блуждающие символы Юникода: в некоторых случаях вам нужно использовать hexeditor или другой редактор/просмотрщик в вашем источнике. Некоторые проблемы не могут быть найдены только при просмотре вашего кода.

    • Попробуйте grep --color -P -n "\[\x80-\xFF\]" file.php в качестве первой меры, чтобы найти не-ASCII символы.

    • В частности, спецификации, пробелы нулевой ширины или неразрывные пробелы и регулярные умные кавычки могут найти свой путь в исходный код.

  • Позаботьтесь о том, какой тип переносов строк сохраняется в файлах.

    • PHP только чтит \n переводы строк, а не \r возврат каретки.

    • Что иногда является проблемой для пользователей MacOS (даже в OS X для неправильно настроенных редакторов).

    • Часто проблема возникает только при использовании однострочных комментариев // или #. Многострочные комментарии /*...*/ редко мешают анализатору, когда /*...*/ игнорируются.

  • Если ваша синтаксическая ошибка не передается через Интернет: бывает, что на вашем компьютере есть синтаксическая ошибка. Но размещение того же самого файла в Интернете больше не демонстрирует его. Что может означать только одну из двух вещей:

    • Вы смотрите не на тот файл!

    • Или ваш код содержал невидимый блуждающий Unicode (см. Выше). Вы можете легко узнать: просто скопируйте свой код обратно из веб-формы в текстовый редактор.

  • Проверьте свою версию PHP. Не все синтаксические конструкции доступны на каждом сервере.

    • php -v для интерпретатора командной строки

    • <?php phpinfo(); за тот, который вызывается через веб-сервер.


    Это не обязательно то же самое. В частности, при работе с фреймворками вы будете их сопоставлять.

  • Не используйте зарезервированные ключевые слова PHP в качестве идентификаторов для функций/методов, классов или констант.

  • Метод проб и ошибок - ваше последнее средство.

Если ничего не помогает, вы всегда можете погуглить ваше сообщение об ошибке. Синтаксические символы не так легко найти (хотя переполнение стека индексируется SymbolHound). Поэтому может потребоваться просмотреть еще несколько страниц, прежде чем вы найдете что-то актуальное.

Дальнейшие руководства:

Белый экран смерти

Если ваш сайт просто пустой, то причиной обычно является синтаксическая ошибка. Включить их отображение с помощью:

  • error_reporting = E_ALL
  • display_errors = 1

В вашем php.ini вообще, или через .htaccess для mod_php, или даже .user.ini с настройками FastCGI.

Включение этого в сломанном скрипте слишком поздно, потому что PHP не может даже интерпретировать/запустить первую строку. Быстрый обходной путь - создание сценария-оболочки, скажем test.php:

<?php
   error_reporting(E_ALL);
   ini_set("display_errors", 1);
   include("./broken-script.php");

Затем вызовите ошибочный код, обратившись к этому сценарию оболочки.

Это также помогает включить PHP error_log и заглянуть в ваш error.log веб-сервера, когда сценарий дает сбой с ответами HTTP 500.

  • 0
    error_reporting(E_ALL | E_STRICT); для более ранних версий PHP
  • 2
    Некоторые IDE (например, NetBeans) поддерживают не только подсветку синтаксиса, но и форматирование кода. Если вы привыкли правильно форматировать свой код и просить IDE переформатировать на всякий случай время от времени, вы можете заметить проблемы, такие как непревзойденные скобки.
94

Я думаю, что эта тема полностью перегружена/сложна. Использование IDE - это способ избежать ошибок синтаксиса. Я бы даже сказал, что работа без IDE является непрофессиональной. Зачем? Поскольку современные IDE проверяют ваш синтаксис после каждого вводимого вами символа. Когда вы кодируете, и вся ваша строка становится красной, и большое предупреждение показывает вам точный тип и точное положение синтаксической ошибки, тогда абсолютно нет необходимости искать другое решение.

Использование синтаксической проверки IDE означает:

Вы (эффективно) никогда не столкнетесь с синтаксическими ошибками снова, просто потому, что видите их правильно по мере ввода. Шутки в сторону.

Отличные IDE с проверкой синтаксиса (все они доступны для Linux, Windows и Mac):

  1. NetBeans [бесплатно]
  2. PHPStorm [$ 199 USD]
  3. Eclipse с плагином PHP [бесплатно]
  4. Sublime [$ 80 USD] (в основном текстовый редактор, но расширяемый с помощью плагинов, таких как PHP Syntax Parser)
  • 1
    Это очевидно. Однако, ссылаясь на IDE здесь, не могли бы вы немного рассказать, где они различаются по синтаксической полезности? Sublime - это в основном редактор, а не IDE; но потом еще красивее и острее; делает в основном только подсветку синтаксиса, но также подходит для сопоставления скобок. Например, он легко обнаруживает ошибки T_CONSTANT_AND_ENCAPSED мгновенно, в отличие от PHPStorm; который, однако, делает более волнистые линии для встроенных ошибок. Синтаксические подсказки NetBeans раньше были более загадочными, чем даже PHP (скорее, с учетом разрешенных конструкций). Можете поделиться своим опытом по плюсам / минусам; ваш любимый Eclipse / PDT или ..?
  • 0
    @mario Я думаю, что вы действительно глубоко разбираетесь в теме, поэтому я действительно не хочу говорить что-то не так здесь, но весь код, который я (и мои товарищи по команде, друзья, которые пишут, фрилансеры) когда-либо писали в IDE, никогда не выполнялся с синтаксической ошибкой. Поэтому я думаю, что, по крайней мере, синтаксическая проверка Netbeans / PHPStorm чрезвычайно мощная. Но, возможно, я неправильно понял ваш вопрос. Дай мне несколько часов ...;)
Показать ещё 3 комментария
48

Неожиданный [

В эти дни, неожиданная [ скобка массива обычно рассматриваются на устаревшие версии PHP. Синтаксис короткого массива доступен начиная с PHP > = 5.4. Более старые установки поддерживают только array().

$php53 = array(1, 2, 3);
$php54 = [1, 2, 3];
         ⇑

Разыменование результата функции массива также недоступно для более старых версий PHP:

$result = get_whatever()["key"];
                      ⇑

Справка - Что означает эта ошибка в PHP? - "Синтаксическая ошибка, неожиданная \[ " показывает наиболее распространенные и практические обходные пути.

Тем не менее, вам всегда лучше просто обновить установку PHP. Для общих планов SetHandler php56-fcgi можно ли использовать SetHandler php56-fcgi, чтобы включить более новую среду выполнения.

Смотрите также:

Кстати, есть также препроцессоры и преобразователи синтаксиса PHP 5.4, если вы действительно цепляетесь за более старые + более медленные версии PHP.

Другие причины для неожиданного [ синтаксические ошибки

Если это не несоответствие версии PHP, то это часто простая синтаксическая ошибка или ошибка синтаксиса новичка:

  • Вы не можете использовать объявления/выражения свойств массива в классах, даже в PHP 7.

    protected $var["x"] = "Nope";
                  ⇑
    
  • Путать [ с открывающимися фигурными скобками { или круглыми скобками ( это распространенный недосмотр).

    foreach [$a as $b)
            ⇑
    

    Или даже:

    function foobar[$a, $b, $c] {
                   ⇑
    
  • Или пытаться разыменовать константы (до PHP 5.6) как массивы:

    $var = const[123];
           ⇑
    

    По крайней мере, PHP интерпретирует это const как постоянное имя.

    Если вы хотели получить доступ к переменной массива (что является типичной причиной здесь), то добавьте начальный $ sigil - так он станет $varname.

  • Вы пытаетесь использовать ключевое слово global для члена ассоциативного массива. Это неверный синтаксис:

    global $var['key'];
    


Неожиданно ] закрывающая квадратная скобка

Это несколько реже, но есть также синтаксические аварии с завершающим массивом ] скобка.

  • Опять несоответствие с ) круглые скобки или } фигурные скобки являются общими:

    function foobar($a, $b, $c] {
                              ⇑
    
  • Или пытаться завершить массив, где его нет:

    $var = 2];
    

    Что часто происходит в объявлениях многострочных и вложенных массивов.

    $array = [1,[2,3],4,[5,6[7,[8],[9,10]],11],12]],15];
                                                 ⇑
    

    Если да, то использовать IDE для согласования кронштейна, чтобы найти преждевременное ] закрытие массива. По крайней мере, используйте больше пробелов и новых строк, чтобы сузить его.

42

Неожиданный T_VARIABLE

"Неожиданное T_VARIABLE " означает, что существует буквальное имя $variable, которое не вписывается в текущую структуру выражения/оператора.

Изображение 733

  1. Отсутствует точка с запятой

    Это чаще всего указывает на отсутствующую точку с запятой в предыдущей строке. Переменные присваивания, следующие за выражением, являются хорошим показателем, на который следует обратить внимание:

           ⇓
    func1()
    $var = 1 + 2;     # parse error in line +2
    
  2. Конкатенация строк

    Частые неудачи - это конкатенации строк с забытыми . оператор:

                                   ⇓
    print "Here comes the value: "  $value;
    

    Кстати, вы должны предпочесть строчную интерполяцию (базовые переменные в двойных кавычках), когда это помогает читаемости. Это позволяет избежать этих синтаксических проблем.

    Строковая интерполяция - это основная функция языка сценариев. Не стыдно использовать его. Игнорируйте любую рекомендацию по микрооптимизации относительно переменной . ускорение конкатенации. Не это.

  3. Отсутствующие операторы выражения

    Конечно, одна и та же проблема может возникнуть в других выражениях, например арифметических операций:

               ⇓
    print 4 + 7 $var;
    

    PHP не может угадать здесь, если переменная должна быть добавлена, вычтена или сравнена и т.д.

  4. Списки

    То же самое для списков синтаксиса, например, в массивах, где парсер также указывает ожидаемую запятую , например:

                                          ⇓
    $var = array("1" => $val, $val2, $val3 $val4);
    

    Или списки параметров функций:

                                    ⇓
    function myfunc($param1, $param2 $param3, $param4)
    

    Эквивалентно вы видите это со list или global утверждениями или при отсутствии ; точка с запятой в цикле for.

  5. Объявления классов

    Эта ошибка парсера также встречается в объявлениях классов. Вы можете назначать только статические константы, а не выражения. Таким образом, парсер жалуется на переменные в качестве назначенных данных:

    class xyz {      ⇓
        var $value = $_GET["input"];
    

    Непревзойденные } закрывающиеся фигурные скобки могут, в частности, привести сюда. Если метод заканчивается слишком рано (используйте правильный отступ!), Тогда блуждающая переменная обычно неправильно помещается в тело объявления класса.

  6. Переменные после идентификаторов

    Вы также можете никогда не иметь переменную, следуя за идентификатором напрямую:

                 ⇓
    $this->myFunc$VAR();
    

    Кстати, это распространенный пример, когда, возможно, предполагалось использовать переменные переменные. В этом случае поиск свойства переменной с помощью $this->{"myFunc$VAR"}(); например.

    Имейте в виду, что использование переменных переменных должно быть исключением. Новички часто пытаются использовать их слишком случайно, даже когда массивы будут проще и более уместны.

  7. Отсутствие парсов после языковых конструкций

    Скорейшее типирование может привести к забытой открывающей скобке для операторов if и for и foreach:

           ⇓
    foreach $array as $key) {
    

    Решение: добавьте недостающее открытие ( между оператором и переменной.

  8. Else не ожидает условий

         ⇓
    else ($var >= 0)
    

    Решение. Удалите условия из else или используйте elseif.

  9. Необходимые скобки для закрытия

         ⇓
    function() uses $var {}
    

    Решение. Добавьте скобки вокруг $var.

  10. Невидимые пробелы

    Как упоминалось в справочном ответе "Невидимый бездомный Юникод" (например, неразрывное пространство), вы также можете увидеть эту ошибку для ничего не подозревающего кода:

    <?php
                              ⇐
    $var = new PDO(...);
    

    Это довольно распространено в начале файлов и для копирования и вставки кода. Проверьте с помощью шестнадцатеричного кода, если ваш код визуально не содержит синтаксическую проблему.

Смотрите также

31

Неожиданное T_CONSTANT_ENCAPSED_STRING
Неожиданный T_ENCAPSED_AND_WHITESPACE

T_CONSTANT_ENCAPSED_STRING имена T_CONSTANT_ENCAPSED_STRING и T_ENCAPSED_AND_WHITESPACE относятся к цитированным "string" литералам.

Они используются в разных контекстах, но проблема синтаксиса весьма схожа. T_ENCAPSED... предупреждения встречаются в контексте с двойной кавычкой строки, в то время как T_CONSTANT... строки часто сбиваются с помощью простых выражений или утверждений PHP.

  1. Неверная переменная интерполяция

    И это чаще всего встречается при некорректной интерполяции переменных PHP:

                              ⇓     ⇓
    echo "Here comes a $wrong['array'] access";
    

    Цитирование ключей массивов является обязательным в контексте PHP. Но в двойных кавычках (или HEREDOC) это ошибка. Парсер жалуется на содержащуюся в одиночном кавычке 'string', потому что обычно он ожидает там литерального идентификатора/ключа.

    Точнее, это справедливо для использования простого синтаксиса в стиле PHP2 в двойных кавычках для ссылок на массивы:

    echo "This is only $valid[here] ...";
    

    Вложенные массивы или более глубокие ссылки на объекты, однако, требуют синтаксиса сложного фигурного синтаксиса:

    echo "Use {$array['as_usual']} with curly syntax.";
    

    Если вы не уверены, это обычно безопаснее использовать. Он часто даже считается более читаемым. И лучшие IDE на самом деле используют для этого разную синтаксическую раскраску.

  2. Отсутствует конкатенация

    Если строка следует за выражением, но не имеет конкатенации или другого оператора, то вы увидите, что PHP жалуется на строковый литерал:

                           ⇓
    print "Hello " . WORLD  " !";
    

    Хотя это очевидно для вас и меня, PHP просто не может догадаться, что строка должна быть добавлена туда.

  3. Сбивающие с толку строковые кавычки

    Такая же синтаксическая ошибка возникает при смешивании строковых разделителей. Строка запускается один ' или двойной " цитаты и заканчивается тем же.

                    ⇓
    print "<a href="' . $link . '">click here</a>";
          ⌞⎽⎽⎽⎽⎽⎽⎽⎽⌟⌞⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⌟⌞⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⎽⌟
    

    Этот пример начинался с двойных кавычек. Но двойные кавычки также предназначались для атрибутов HTML. Предполагаемый оператор конкатенации внутри, однако, интерпретировался как часть второй строки в одинарных кавычках.

    Совет. Установите редактор /IDE для использования слегка отличной раскраски для одиночных и двойных кавычек. (Это также помогает с логикой приложения, например, использовать двойные кавычки для текстового вывода и одиночные кавычки только для константоподобных значений.)

    Это хороший пример, когда вы не должны выходить из двойных кавычек в первую очередь. Вместо этого просто используйте правильные \" для атрибутов HTML-атрибутов":

    print "<a href=\"{$link}\">click here</a>";
    

    Хотя это также может привести к путанице в синтаксисе, все лучшие IDE/редакторы снова помогают раскрасить экранированные кавычки по-разному.

  4. Отсутствует стартовая цитата

    Эквивалентно забытое открытие "/' цитирует рецепт ошибок парсера:

                   ⇓
     make_url(login', 'open');
    

    Здесь ', ' станет строковым литералом после голого слова, когда, очевидно, login должен быть строковым параметром.

  5. Списки массивов

    Если вы пропустите , запятая в блоке создания массива, анализатор будет видеть две последовательные строки:

    array(               ⇓
         "key" => "value"
         "next" => "....",
    );
    

    Обратите внимание, что в последней строке всегда может содержаться дополнительная запятая, но игнорировать одно между ними непростительно. Это трудно обнаружить без подсветки синтаксиса.

  6. Списки параметров функции

    То же самое для вызовов функций:

                             ⇓
    myfunc(123, "text", "and"  "more")
    
  7. Беглые строки

    Общим вариантом являются довольно просто забытые терминаторы строк:

                                    ⇓
    mysql_evil("SELECT * FROM stuffs);
    print "'ok'";
          ⇑
    

    Здесь PHP жалуется на два строковых литерала, непосредственно следуя друг за другом. Но настоящая причина - незакрытая предыдущая строка, конечно.

Смотрите также

22

Неожиданный T_STRING

T_STRING является немного неправильным. Он не относится к цитируемой "string". Это означает, что был обнаружен необработанный идентификатор. Это может быть от bare слов до оставшихся CONSTANT или имен функций, забытых строк без кавычек или любого простого текста.

  1. Неверные строки

    Однако эта синтаксическая ошибка является наиболее распространенной для неверных строк. Любая неопределенная и бродячая " или ' цитата образует недопустимое выражение:

                   ⇓                  ⇓
     echo "<a href="http://example.com">click here</a>";
    

    Выделение синтаксиса сделает такие ошибки супер очевидными. Важно помнить об использовании обратных косых черт для экранирования \" двойных кавычек" или \' одиночных кавычек" - в зависимости от того, что использовалось как оболочка строки.

    • Для удобства вы должны предпочесть внешние одинарные кавычки при выводе простого HTML с двойными кавычками внутри.
    • Используйте двойные кавычки, если вы хотите интерполировать переменные, но затем следите за тем, чтобы избежать буквенных " двойных кавычек".
    • Для более длинного выхода предпочитайте несколько строк echo/print вместо вылета и выхода. Еще лучше рассмотрим раздел HEREDOC.

    См. Также В чем разница между строками с одним кавычком и двойными кавычками в PHP? ,

  2. Незакрытые строки

    Если вы пропустите закрытие " тогда синтаксическая ошибка, как правило, будет реализована позже. Непривязанная строка будет часто потреблять бит кода до следующего предполагаемого значения строки:

                                                           ⇓
    echo "Some text", $a_variable, "and some runaway string ;
    success("finished");
             ⇯
    

    Это не просто буквальный T_STRING который парсер может протестовать тогда. Еще одним частым изменением является Unexpected '>' для некотируемого буквального HTML.

  3. Непрограммируемые строковые кавычки

    Если вы копируете и вставляете код из блога или веб-сайта, иногда вы получаете неверный код. Типографические котировки не соответствуют ожиданиям PHP:

    $text = Something something.. + "these ain't quotes";
    

    Типографические/умные кавычки являются символами Юникода. PHP рассматривает их как часть смежного алфавитно-цифрового текста. Например, "these интерпретируются как константный идентификатор, но любой последующий текстовый литерал затем рассматривается как гонор /T_STRING парсером.

  4. Отсутствует точка с запятой; еще раз

    Если у вас есть неисчерпаемое выражение в предыдущих строках, любая следующая инструкция или языковая конструкция рассматривается как необработанный идентификатор:

           ⇓
    func1()
    function2();
    

    PHP просто не может знать, хотите ли вы запустить две функции за другой, или если вы хотели бы умножить их результаты, добавить их, сравнить их или запустить только один || или другой.

  5. Короткие открытые теги и заголовки <?xml в скриптах PHP

    Это довольно редко. Но если short_open_tags включены, то вы не можете начинать свои PHP-скрипты с объявления XML:

          ⇓
    <?xml version="1.0"?>
    

    PHP увидит <? и вернуть его для себя. Он не поймет, для чего предназначен бродячий xml. Он будет интерпретироваться как постоянный. Но version будет рассматриваться как еще один литерал/константа. И поскольку анализатор не может понять два последующих литерала/значения без оператора выражения между ними, это будет сбой парсера.

  6. Невидимые символы Юникода

    Самой отвратительной причиной для синтаксических ошибок являются символы Юникода, такие как неразрывное пространство. PHP позволяет использовать символы Unicode в качестве имен идентификаторов. Если вы получаете жалобу на парсер T_STRING для совершенно невосприимчивого кода, например:

    <?php
        print 123;
    

    Вам нужно вырвать другой текстовый редактор. Или даже гекседектор. То, что выглядит как простые пространства и новые строки здесь, может содержать невидимые константы. Java-IDE иногда не обращают внимания на спецификацию UTF-8, искаженные внутри, пространства с нулевой шириной, разделители абзацев и т.д. Попытайтесь переиздать все, удалить пробелы и снова добавить обычные пробелы.

    Вы можете сузить его, добавив избыточность ; разделители операторов при каждом запуске линии:

    <?php
        ;print 123;
    

    Дополнительный ; точка с запятой преобразует предыдущий невидимый символ в неопределенную константную ссылку (выражение как выражение). Это в свою очередь делает PHP полезным уведомлением.

  7. Знак '$' отсутствует перед именами переменных

    Переменные в PHP представлены знаком доллара, за которым следует имя переменной.

    Знак доллара ($) - это сигила, которая обозначает идентификатор как имя переменной. Без этого символа идентификатор может быть ключевым словом языка или константой.

    Это обычная ошибка, когда код PHP был "переведен" из кода, написанного на другом языке (C, Java, JavaScript и т.д.). В таких случаях декларация типа переменной (когда исходный код был написан на языке, который использует типизированные переменные) также мог прокрасться и произвести эту ошибку.

  8. Исключенные котировочные знаки

    Если вы используете \ в строке, это имеет особое значение. Это называется " Escape Character " и обычно говорит парсеру буквально воспринимать следующий символ.

    Пример: echo 'Jim said \'Hello\''; будет печатать Jim said 'hello'

    Если вы избежите закрывающей цитаты строки, заключительная цитата будет взята буквально и не так, как предполагалось, то есть в качестве печатной цитаты как части строки, а не для закрытия строки. Это будет отображаться как ошибка разбора, обычно после открытия следующей строки или в конце скрипта.

    Очень распространенная ошибка при указании путей в Windows: "C:\xampp\htdocs\" неверна. Вам нужно "C:\\xampp\\htdocs\\".

15

Неожиданный (

Открывающиеся круглые скобки обычно следуют языковым конструкциям, таким как if/foreach/for/array/list или запускают арифметическое выражение. Они синтаксически неверны после "strings", предыдущего (), одиночного $ и в некоторых типичных контекстах объявления.

  1. Параметры объявления функции

    Редкое появление этой ошибки пытается использовать выражения в качестве параметров функции по умолчанию. Это не поддерживается даже в PHP7:

    function header_fallback($value, $expires = time() + 90000) {
    

    Параметры в объявлении функции могут быть только литеральными значениями или постоянными выражениями. В отличие от функций invocations, где вы можете свободно использовать whatever(1+something()*2) и т.д.

  2. По умолчанию свойства класса

    То же самое для деклараций членов класса, где допускаются только значения литерала/константы, а не выражения:

    class xyz {                   ⇓
        var $default = get_config("xyz_default");
    

    Поместите такие вещи в конструктор. См. Также Почему атрибуты PHP не позволяют выполнять функции?

    Снова отметим, что PHP 7 допускает только var $xy = 1 + 2 +3; там постоянные выражения.

  3. Синтаксис JavaScript в PHP

    Использование синтаксиса JavaScript или jQuery не будет работать на PHP по понятным причинам:

    <?php      ⇓
        print $(document).text();
    

    Когда это происходит, оно обычно указывает на неисчерпаемую предыдущую строку; и буквальные <script> разделы, попадающие в контекст кода PHP.

  4. isset (()), пустой, ключ, следующий, текущий

    И isset() и empty() являются языковыми встроенными, а не функциями. Им нужно получить доступ к переменной напрямую. Если вы слишком часто добавляете пару круглых скобок, вы должны создать выражение:

              ⇓
    if (isset(($_GET["id"]))) {
    

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

    Функции уровня пользователя, требующие ссылки на переменные -but, получают результат выражения passed-, вместо этого приводят к ошибкам во время выполнения.


Неожиданно )

  1. Отсутствует параметр функции

    Вы не можете запятнать запятую в вызове функции. PHP ожидает там ценности и, следовательно, жалуется на скорую скобки ).

                  ⇓
    callfunc(1, 2, );
    

    Конечная запятая допускается только в конструкциях array() или list().

  2. Неоконченные выражения

    Если вы забудете что-то в арифметическом выражении, тогда парсер сдастся. Потому что как это может интерпретировать это:

                   ⇓
    $var = 2 * (1 + );
    

    И если вы забыли закрыть ), тогда вы получите жалобу на неожиданную точку с запятой.

  3. Foreach как constant

    Для забытых переменных $ префиксов в управляющих операциях вы увидите:

                       ↓    ⇓
    foreach ($array as wrong) {
    

    PHP здесь иногда говорит вам, что он ожидал a :: вместо этого. Поскольку переменная class :: $ могла удовлетворять ожидаемому выражению $ variable.


Неожиданный {

Кудрявые фигурные скобки { и } заключают блоки кода. И ошибки синтаксиса в отношении них обычно указывают на некорректное вложенность.

  1. Непревзойденные подвыражения в if

    Чаще всего неуравновешенные ( и ) являются причиной, если парсер жалуется на открытие курчавого { появляется слишком рано. Простой пример:

                                  ⇓
    if (($x == $y) && (2 == true) {
    

    Подсчитайте свои parens или используйте IDE, которая помогает с этим. Также не пишите код без пробелов. Показатели удобочитаемости.

  2. {и} в контексте выражения

    Вы не можете использовать фигурные скобки в выражениях. Если вы путаете круглые скобки и кудри, это не будет соответствовать языковому грамматику:

               ⇓
    $var = 5 * {7 + $x};
    

    Для построения идентификатора существует несколько исключений, таких как локальная переменная области ${references}.

  3. Переменные переменные или фигурные выражения var

    Это довольно редко. Но вы также можете получить { и } жалобы парсера на сложные выражения переменных:

                          ⇓
    print "Hello {$world[2{]} !";
    

    Хотя есть более высокая вероятность неожиданного } в таких контекстах.


Неожиданный }

При получении "неожиданную } " ошибка, вы в основном закрыли блок кода слишком рано.

  1. Последний оператор в кодовом блоке

    Это может случиться для любого неисчерпаемого выражения.

    И если в последней строке в блоке функции/кода отсутствует трейлинг ; точка с запятой:

    function whatever() {
        doStuff()
    }            ⇧
    

    Здесь синтаксический анализатор не может определить, хотите ли вы еще добавить + 25; к результату функции или чему-то еще.

  2. Недопустимое вложенность блоков/Забытое {

    Иногда вы увидите эту ошибку парсера, когда блок кода был } закрыт слишком рано или вы забыли открытие { even:

    function doStuff() {
        if (true)    ⇦
            print "yes";
        }
    }   ⇧
    

    В вышеприведенном фрагменте, if не было открытия { фигурная скобка. Таким образом, закрытие } одного ниже стало излишним. И поэтому следующее закрытие }, которое предназначалось для функции, не было связано с первоначальным открытием { фигурной скобки.

    Такие ошибки еще труднее найти без правильного ввода кода. Используйте сопоставление IDE и скобок.


Неожиданный {, ожидающий (

Языковые конструкции, для которых требуется заголовок условия/декларации и блок кода, вызовут эту ошибку.

  1. Списки параметров

    Например, недопустимые функции без списка параметров не разрешены:

                     ⇓
    function whatever {
    }
    
  2. Условия контрольной инструкции

    И вы также не можете иметь, if без условия.

      ⇓
    if {
    }
    

    Очевидно, это не имеет смысла. То же самое для обычных подозреваемых, for/foreach, while/do и т.д.

    Если у вас есть эта конкретная ошибка, вы определенно должны найти некоторые примеры руководства.

  • 1
    Я искал ответ на мой вопрос в этом посте, но сам нашел ответ на проблему - «Неожиданный {», поэтому я хотел поделиться с моим ответом - для меня проблема заключалась в кодировании разрыва строки - каким-то образом некоторые из моих В файлах использовались разрывы строк в Macintosh, но когда я изменил их на разрывы строк в Windows - моя проблема (на локальном хосте (WAMP) все работает, но на веб-сервере linux нет) была решена.
  • 0
    @EdgarsAivars Спасибо за ваш комментарий! Разрывы строк для конкретных платформ - действительно редкая и сложная проблема. Я, наверное, упомяну это и здесь. (Это было только что упомянуто в стороне в другом справочном ответе .)
Показать ещё 1 комментарий
14

Неожиданный конец $

Когда PHP говорит о "неожиданном $end ", это означает, что ваш код закончился преждевременно. (Это сообщение немного вводит в заблуждение, если принять его буквально. Это не о переменной с именем "end end", иногда предполагаемой новичками. Она относится к "концу файла", EOF.)

Причина. Небаланс { и } для кодовых блоков/и объявлений функций или классов.

Это почти всегда о пропавшей } фигурной скобки, чтобы закрыть предшествующие блоки кода.

  • Опять же, используйте правильные отступы, чтобы избежать таких проблем.

  • Используйте IDE с привязкой к скобкам, чтобы узнать, где }. В большинстве IDE и текстовых редакторах есть сочетания клавиш:

    • NetBeans, PhpStorm, Komodo: Ctrl [ и Ctrl ]
    • Eclipse, Aptana: Ctrl Shift P
    • Atom, Sublime: Ctrl m - Zend Studio Ctrl M
    • Geany, Notepad++: Ctrl B - Джо: Ctrl G - Emacs: C-M-n - Vim: %

Большинство IDE также выделяют соответствующие фигурные скобки, скобки и круглые скобки. Это позволяет довольно легко проверить их соотношение:

Изображение 734

Неограниченные выражения

И Unexpected $end ошибка синтаксиса/парсера Unexpected $end также может возникать для неиспользуемых выражений или операторов:

  • $var = func(1, ?> EOF

Итак, сначала посмотрите на конец скриптов. Конечный ; часто избыточно для последнего оператора в любом скрипте PHP. Но у вас должен быть такой. Именно потому, что он сужает такие проблемы синтаксиса.

Отметные маркеры HEREDOC

Еще одно распространенное явление появляется в строках HEREDOC или NOWDOC. Конечный маркер игнорируется ведущими пробелами, вкладками и т. Д.:

print <<< END
    Content...
    Content....
  END;
# ↑ terminator isn't exactly at the line start

Поэтому анализатор предполагает, что строка HEREDOC продолжается до конца файла (отсюда "Неожиданный конец $"). Практически все IDE и редакторы с подсветкой синтаксиса сделают это очевидным или предупредит об этом.

Исключенные котировочные знаки

Если вы используете \ в строке, это имеет особое значение. Это называется " Escape Character " и обычно говорит парсеру буквально воспринимать следующий символ.

Пример: echo 'Jim said \'Hello\''; будет печатать Jim said 'hello'

Если вы избежите закрывающей цитаты строки, заключительная цитата будет взята буквально и не так, как предполагалось, то есть в качестве печатной цитаты как части строки, а не для закрытия строки. Это будет отображаться как ошибка разбора, обычно после открытия следующей строки или в конце скрипта.

Очень распространенная ошибка при указании путей в Windows: "C:\xampp\htdocs\" неверна. Вам нужно "C:\\xampp\\htdocs\\".

Альтернативный синтаксис

Несколько реже вы можете увидеть эту синтаксическую ошибку при использовании альтернативного синтаксиса для операторов/блоков кода в шаблонах. Использование if: и else: и отсутствующий endif; например.

Смотрите также:

13

Неожиданный T_IF
Неожиданный T_ELSEIF
Неожиданный T_ELSE
Неожиданный T_ENDIF

Условные блоки управления, if, elseif и else следуют простой структуре. Когда вы сталкиваетесь с синтаксической ошибкой, скорее всего, это просто недопустимое вложение блоков → с отсутствующими { фигурные скобки } - или слишком много.

Изображение 735

  1. Отсутствует { или } из-за неправильного отступа

    Несоответствующие скобки кода являются общими для менее хорошо отформатированного кода, например:

    if((!($opt["uniQartz5.8"]!=$this->check58)) or (empty($_POST['poree']))) {if
    ($true) {echo"halp";} elseif((!$z)or%b){excSmthng(False,5.8)}elseif (False){
    

    Если ваш код выглядит так, начните заново! В противном случае это невозможно для вас или кого-либо еще. Нет смысла демонстрировать это в Интернете, чтобы узнать о помощи.

    Вы сможете только исправить это, если вы можете визуально следовать вложенной структуре и соотношению условий if/else и их { кодовых блоков }. Используйте свою среду IDE, чтобы узнать, все ли они спарены.

    if (true) {
         if (false) {
                  …
         }
         elseif ($whatever) {
             if ($something2) {
                 …
             } 
             else {
                 …
             }
         }
         else {
             …
         }
         if (false) {    //   a second 'if' tree
             …
         }
         else {
             …
         }
    }
    elseif (false) {
        …
    }
    

    Любой double } } не просто закрывает ветвь, а предыдущую структуру условий. Поэтому придерживайтесь одного стиля кодирования; не смешивайте и не сопоставляйте вложенные деревья if/else.

    Помимо согласованности здесь, оказывается полезным также избегать длительных условий. Используйте временные переменные или функции, чтобы избежать нечитаемых, if -expressions.

  2. IF не может использоваться в выражениях

    Неожиданно частая ошибка новичков пытается использовать оператор if в выражении, например, выражение печати:

                       ⇓
    echo "<a href='" . if ($link == "example.org") { echo …
    

    Конечно, это неверно.

    Вы можете использовать тернарный условный, но остерегайтесь уязвимости.

    echo "<a href='" . ($link ? "http://yes" : "http://no") . "</a>";
    

    В противном случае сломайте такие выходные конструкции: используйте несколько if и echo s.
    Еще лучше использовать временные переменные и поместить свои условные обозначения до:

    if ($link) { $href = "yes"; } else { $href = "no"; }
    echo "<a href='$href'>Link</a>";
    

    Определение функций или методов для таких случаев часто имеет смысл.

    Блоки управления не возвращают "результаты"

    Теперь это менее распространено, но несколько кодеров даже пытаются лечить, if так, как будто это могло вернуть результат:

    $var = if ($x == $y) { "true" };
    

    Это структурно идентично использованию, if внутри конкатенации/выражения строки.

    • Но структуры управления (если /foreach/while) не имеют "результата".
    • Литеральная строка "true" также будет просто выражением void.

    Вам нужно будет использовать назначение в кодовом блоке:

    if ($x == $y) { $var = "true"; }
    

    С другой стороны, прибегает к ?: трехкомпонентному сравнению.

    Если в If

    Вы не можете вложить if внутри условия:

                        ⇓
    if ($x == true and (if $y != false)) { ... }
    

    Это явно избыточно, потому что and (или or) уже позволяет сравнивать цепочку.

  3. Забытый ; точка с запятой

    Еще раз: каждый блок управления должен быть инструкцией. Если предыдущий фрагмент кода не заканчивается точкой с запятой, то это гарантированная синтаксическая ошибка:

                    ⇓
    $var = 1 + 2 + 3
    if (true) { … }
    

    Btw, последняя строка в блоке кода {…} требует точку с запятой.

  4. Точка с запятой слишком ранняя

    Теперь, вероятно, неправильно винить определенный стиль кодирования, поскольку эту ловушку слишком легко упускать из виду:

                ⇓
    if ($x == 5);
    {
        $y = 7;
    }
    else           ←
    {
        $x = -1;    
    }
    

    Что происходит чаще, чем вы могли себе представить.

    • Когда вы завершаете выражение if() ; он выполнит оператор void. ; становится пустой {} !
    • Таким образом, блок {…} отделяется от if и всегда запускается.
    • Таким образом, у else больше не было отношения к открытой конструкции if, поэтому это привело бы к неожиданной синтаксической ошибке T_ELSE.

    Это также объясняет также тонкую вариацию этой синтаксической ошибки:

    if ($x) { x_is_true(); }; else { something_else(); };
    

    Где ; после того, как блок кода {…} завершает целое, if конструкция, отрезая else ветвь синтаксически.

  5. Не использовать блоки кода

    Синтаксически это позволяло пропускать фигурные скобки {... } для блоков кода в ветвях if/elseif/else. К сожалению, стиль синтаксиса очень распространен для неперевернутых кодировщиков. (По ложному предположению это было бы быстрее ввести или прочитать).

    Однако это очень вероятно, чтобы отключить синтаксис. Рано или поздно дополнительные инструкции найдут свой путь в ветвях if/else:

    if (true)
        $x = 5;
    elseif (false)
        $x = 6;
        $y = 7;     ←
    else
        $z = 0;
    

    Но для фактического использования блоков кода вам нужно написать {... } их как таковые!

    Даже опытные программисты избегают этого бессловесного синтаксиса или, по крайней мере, понимают его как исключительное исключение из правила.

  6. Else/Elseif в неправильном порядке

    Одна вещь, чтобы напомнить себе, конечно, условный порядок.

    if ($a) { … }
    else { … }
    elseif ($b) { … }
    ↑
    

    У вас может быть столько же elseif сколько вам нужно, но else нужно пропустить последнее. Вот как это.

  7. Объявления классов

    Как упоминалось выше, вы не можете иметь контрольные утверждения в объявлении класса:

    class xyz {
        if (true) {
            function ($var) {}
        }
    

    Вы либо забыли функцию определения, или закрыты один } слишком рано в таких случаях.

  8. Неожиданный T_ELSEIF/T_ELSE

    При смешивании PHP и HTML закрытие } для if/elseif должно быть в том же блоке PHP <?php?> elseif/else в следующем elseif/else. Это приведет к ошибке, поскольку закрытие } для if должно быть частью elseif:

    <?php if ($x) { ?>
        html
    <?php } ?>
    <?php elseif ($y) { ?>
        html
    <?php } ?>
    

    Правильная форма <?php } elseif:

    <?php if ($x) { ?>
        html
    <?php } elseif ($y) { ?>
        html
    <?php } ?>
    

    Это более или менее вариация неправильного отступа - по-видимому, часто основанная на неправильных намерениях кодирования.
    Вы не можете смять другие утверждения между ними, if и elseif/else структурные маркеры:

    if (true) {
    }
    echo "in between";    ←
    elseif (false) {
    }
    ?> text <?php      ←
    else {
    }
    

    Либо может произойти только в {…} блоках кода, а не между маркерами контрольной структуры.

    • В любом случае это не имеет смысла. Не похоже, что было какое-то "неопределенное" состояние, когда PHP перескакивает между ветвями if и else.
    • Вы должны решить, где печатные заявления принадлежат/или если их необходимо повторить в обеих ветвях.

    Вы также не можете разделить if/else между различными структурами управления:

    foreach ($array as $i) {
        if ($i) { … }
    }
    else { … }
    

    Синтаксической связи между if и else. Лексический диапазон foreach заканчивается на }, поэтому нет смысла продолжать работу if.

  9. T_ENDIF

    Если вы испытываете неожиданный T_ENDIF, вы используете альтернативный стиль синтаксиса, if:elseif:else:endif; , Которые вы должны действительно дважды подумать.

    • Обычная ловушка сбивает с толку сходство : двоеточие ; точка с запятой. (Покрытый в "Точке с запятой слишком рано")

    • Поскольку отступы сложнее отслеживать в файлах шаблонов, тем больше при использовании альтернативного синтаксиса - это правдоподобно для вашего endif; не соответствует, if:

    • Использование } endif; удваивается, if -terminator.

    В то время как "неожиданный конец $", как правило, цена на забыто закрывающую } фигурной скобки.

  10. Назначение против сравнения

    Таким образом, это не синтаксическая ошибка, но стоит упомянуть в этом контексте:

           ⇓
    if ($x = true) { }
    else { do_false(); }
    

    Это не сравнение ==/===, а назначение =. Это довольно тонко и легко приведет некоторых пользователей к беспомощному редактированию блоков всего состояния. Следите за непреднамеренными заданиями сначала - когда вы испытываете логическую ошибку /misbeheviour.

11

Неожиданный T_IF
Неожиданный T_FOREACH
Неожиданный T_FOR
Неожиданный T_WHILE
Неожиданный T_DO
Неожиданный T_ECHO

Управляющие конструкции, такие как if, foreach, for, while, list, global, return, do, print, echo могут использоваться только как заявления. Они обычно живут по одной линии.

  • Точка с запятой; где ты?

    Довольно универсально, если вы пропустили точку с запятой в предыдущей строке, если парсер жалуется на инструкцию управления:

                 ⇓
    $x = myfunc()
    if (true) {
    

    Решение: просмотрите предыдущую строку; добавить точку с запятой.

  • Объявления классов

    Другое место, где это происходит, в объявлениях классов. В разделе класса вы можете только перечислять инициализации свойств и разделы методов. Никакой код не может находиться там.

    class xyz {
        if (true) {}
        foreach ($var) {}
    

    Такие синтаксические ошибки обычно реализуются для неверно вложенных { и }. В частности, когда блоки кода функции закрылись слишком рано.

  • Выражения в контексте выражения

    Большинство языковых конструкций могут использоваться только как утверждения. Они не предназначены для размещения внутри других выражений:

                       ⇓
    $var = array(1, 2, foreach($else as $_), 5, 6);
    

    Аналогично, вы не можете использовать if в строках, математических выражениях или в других местах:

                   ⇓
    print "Oh, " . if (true) { "you!" } . " won't work";
    // Use a ternary condition here instead, when versed enough.
    

    Для вложения if -подобных условий в выражении специально вы часто хотите использовать трехмерную оценку ?:.

    То же самое относится к for, while, global, echo и меньшему расширению list.

              ⇓
    echo 123, echo 567, "huh?";
    

    В то время как print() - это встроенный язык, который может использоваться в контексте выражения. (Но редко имеет смысл.)

  • Зарезервированные ключевые слова как идентификаторы

    Вы также не можете использовать do или if и другие языковые конструкции для пользовательских функций или имен классов. (Возможно, в PHP7. Но даже тогда было бы нецелесообразно.)

10

Неожиданный T_IS_EQUAL
Неожиданный T_IS_GREATER_OR_EQUAL
Неожиданный T_IS_IDENTICAL
Неожиданный T_IS_NOT_EQUAL
Неожиданный T_IS_NOT_IDENTICAL
Неожиданный T_IS_SMALLER_OR_EQUAL
Неожиданный <
Неожиданный >

Операторы сравнения, такие как ==, >=, ===, !=, <>, !== и <= или < и > в основном следует использовать только в выражениях, например, if выражения. Если синтаксический анализатор жалуется на них, это часто означает неправильный paring или mismatched ( ) parens вокруг них.

  1. Группировка Parens

    В частности, для операторов if с несколькими сравнениями вы должны позаботиться о правильном подсчете открывающей и закрывающей круглых скобок:

                            ⇓
    if (($foo < 7) && $bar) > 5 || $baz < 9) { ... }
                          ↑
    

    Здесь условие if здесь уже было прервано )

    После того, как ваши сравнения становятся достаточно сложными, что часто помогает разбить его на несколько и вложенных друг в друга, if конструктов скорее.

  2. isset(), измельченный при сравнении

    Обычным новичком является то, что pitfal пытается совместить isset() или empty() со сравнением:

                            ⇓
    if (empty($_POST["var"] == 1)) {
    

    Или даже:

                        ⇓
    if (isset($variable !== "value")) {
    

    Это не имеет смысла для PHP, потому что isset и empty - это языковые конструкции, которые принимают только имена переменных. Не имеет смысла сравнивать результат либо потому, что вывод только/уже является логическим.

  3. Confusion >= больше или равно с => оператором массива

    Оба оператора выглядят несколько схожими, поэтому их иногда путают:

             ⇓
    if ($var => 5) { ... }
    

    Вам нужно только помнить, что этот оператор сравнения называется "большим или равным", чтобы понять это правильно.

    См. Также: Структура оператора if в PHP

  4. Ничего не сравнится с

    Вы также не можете комбинировать два сравнения, если они относятся к одному и тому же имени переменной:

                     ⇓
    if ($xyz > 5 and < 100)
    

    PHP не может вывести, что вы хотели снова сравнить начальную переменную. Выражения, как правило, в паре в соответствии с оператором старшинства, так что к тому времени, когда < видно, не было бы всего лишь логический результат слева от исходной переменной.

    См. Также: неожиданный T_IS_SMALLER_OR_EQUAL

  5. Цепи сравнения

    Вы не можете сравнивать с переменной с рядом операторов:

                      ⇓
     $reult = (5 < $x < 10);
    

    Это должно быть разбито на два сравнения, каждый против $x.

    На самом деле это больше относится к черным спискам (из-за эквивалентной операторной ассоциативности). Он синтаксически действителен в нескольких языках C-стиля, но PHP не будет интерпретировать его как ожидаемую цепочку сравнения.

  6. Неожиданный >
    Неожиданный <

    Больше > меньше или < операторы не имеют пользовательский T_XXX Tokenizer имени. И хотя они могут быть неуместными, как и все остальные, вы чаще всего видите, что парсер жалуется на них за неверно настроенные строки и вышитые HTML:

                            ⇓
    print "<a href='z">Hello</a>";
                     ↑
    

    Это составляет строка "<a href='z" > буквального постоянной Hello, а затем другой < сравнения. Или, по крайней мере, как это видит PHP. Фактическая причина и синтаксис ошибка была преждевременно строка " окончание.

    Также невозможно вставить теги запуска PHP:

    <?php echo <?php my_func(); ?>
               ↑
    

Смотрите также:

6

Неожиданный '?'

Если вы пытаетесь использовать оператор объединения нулей ?? в версии PHP до PHP 7 вы получите эту ошибку.

<?= $a ?? 2; // works in PHP 7+
<?= (!empty($a)) ? $a : 2; // All versions of PHP

Неожиданное "?", Ожидающая переменная

Аналогичная ошибка может возникать для типов, допускающих значение NULL, например:

function add(?int $sum): ?int {

Что опять же указывает на использование устаревшей версии PHP (либо CLI-версия php -v либо веб-сервер ограничен одним phpinfo();).

5

Неожиданное T_LNUMBER

T_LNUMBER относится к "длинному"/номеру.

  1. Недопустимые имена переменных

    В PHP и большинстве других языков программирования переменные не могут начинаться с числа. Первым символом должен быть алфавит или символ подчеркивания.

    $1   // Bad
    $_1  // Good
    

    Изображение 736

    • Довольно часто возникает вопрос о использовании preg_replace -placeholders "$1" в контексте PHP:

      #                         ↓            ⇓  ↓
      preg_replace("/#(\w+)/e",  strtopupper($1) )
      

      Если обратный вызов должен быть указан. (Теперь флаг /e regex устарел, но иногда он иногда используется неправильно в preg_replace_callback.)

    • То же ограничение идентификатора применяется к свойствам объекта, кстати.

             ↓
      $json->0->value
      
    • Хотя токенизатор/парсер не разрешает буквенное значение $1 как имя переменной, можно использовать ${1} или ${"1"}. Который является синтаксическим обходным решением для нестандартных идентификаторов. (Лучше всего думать об этом как о локальном просмотре области. Но вообще: предпочитайте простые массивы для таких случаев!)

    • Любопытно, но очень не рекомендуется, парсер PHPs позволяет Unicode-идентификаторы; такой, что $➊ будет действительным. (В отличие от буква 1).

  2. Вход в массивный массив

    Неожиданное долго также может возникнуть для объявлений массива - при отсутствии , запятые:

    #            ↓ ↓
    $xy = array(1 2 3);
    

    Или же вызовы функций и декларации и другие конструкции:

    • func(1, 2 3);
    • function xy($z 2);
    • for ($i=2 3<$z)

    Так обычно бывает один из них ; или , отсутствует для разделения списков или выражений.

  3. Misquoted HTML

    И опять же, неверные строки являются частым источником бродячих чисел:

    #                 ↓ ↓          
    echo "<td colspan="3">something bad</td>";
    

    Такие случаи следует рассматривать более или менее как неожиданные ошибки T_STRING.

  4. Другие идентификаторы

    Ни функции, ни классы, ни пространства имен не могут быть названы, начиная с номера:

             ↓
    function 123shop() {
    

    Совсем так же, как и для имен переменных.

2

Неожиданный '='

Это может быть вызвано наличием недопустимых символов в имени переменной. Имена переменных должны соответствовать следующим правилам:

Имена переменных следуют тем же правилам, что и другие метки в PHP. Правильное имя переменной начинается с буквы или подчеркивания, за которой следует любое количество букв, цифр или символов подчеркивания. В качестве регулярного выражения оно выражается следующим образом: "[a-zA-Z_\x7f-\xff] [a-zA-Z0-9 _\x7f-\xff] * '

  • 0
    Хорошее дополнение Джон.
1

Неожиданный "продолжить" (T_CONTINUE)

continue - это утверждение (например, для или если) и должно выглядеть автономным. Он не может использоваться как часть выражения. Отчасти потому, что continue не возвращает значение, но в выражении каждое подвыражение должно приводить к некоторому значению, поэтому общее выражение приводит к значению. Это разница между выражением и выражением.

Это означает, что continue не может использоваться в тройном заявлении или в любом заявлении, требующем возвращаемого значения.

Неожиданный "разрыв" (T_BREAK)

То же самое касается break; конечно. Он также неприменим в контексте выражения, но строгий оператор (на том же уровне, что и foreach или блок if).

Неожиданное "возвращение" (T_RETURN)

Теперь это может быть более неожиданным для return, но это также просто оператор уровня блока. Он возвращает значение (или NULL) для более высокой области/функции, но оно не оценивается как само выражение. → То есть: нет смысла делать return(return(false);;

0

Неожиданный "конец" (T_ENDWHILE)

Синтаксис использует двоеточие - при отсутствии двоеточия произойдет вышеуказанная ошибка

<?php while($query->fetch()): ?>
 .... 
<?php endwhile; ?>

Альтернативой этому синтаксису является использование фигурных скобок

<?php while($query->fetch()) { ?>
  ....
<?php } ?>

http://php.net/manual/en/control-structures.while.php

Ещё вопросы

Сообщество Overcoder
Наверх
Меню