Che cosa significa il messaggio di errore PHP "Avviso: uso di costante non definita"?


164

PHP sta scrivendo questo errore nei registri: "Avviso: utilizzo di costante non definita".

Errore nei registri:

PHP Notice:  Use of undefined constant department - assumed 'department' (line 5)
PHP Notice:  Use of undefined constant name - assumed 'name' (line 6)
PHP Notice:  Use of undefined constant email - assumed 'email' (line 7)
PHP Notice:  Use of undefined constant message - assumed 'message' (line 8)

Righe di codice pertinenti:

$department = mysql_real_escape_string($_POST[department]);
$name = mysql_real_escape_string($_POST[name]);
$email = mysql_real_escape_string($_POST[email]);
$message = mysql_real_escape_string($_POST[message]);

Cosa significa e perché lo vedo?

Risposte:


218

Dovresti citare le chiavi dell'array:

$department = mysql_real_escape_string($_POST['department']);
$name = mysql_real_escape_string($_POST['name']);
$email = mysql_real_escape_string($_POST['email']);
$message = mysql_real_escape_string($_POST['message']);

Come è, si era alla ricerca di costanti denominate department, name, email, message, ecc Quando non trova una costante, PHP (stranamente) l'interpreta come una stringa ( 'reparto', ecc). Ovviamente, questo può facilmente rompersi se in seguito viene definita una costante del genere (anche se è un cattivo stile avere costanti minuscole).


Si riferisce alla variabile $ _POST?
Nik,

3
@Col. Shrapnel, quando ho detto che dovevano essere quotate solo le chiavi dell'array? Deve citare le chiavi, ma non solo quelle.
Matthew Flaschen,

1
beh, intendo dire che non c'è bisogno di citare le chiavi dell'array . bisogna citare stringhe, non chiavi array. una chiave non richiede preventivi speciali.
Il tuo buon senso

4
Non è "bizzarro" ... È "retrocompatibile". PHP inizialmente consentiva e addirittura promuoveva l'uso di stringhe non quotate come chiavi. (Va bene, forse è ancora "bizzarro". :-)
Brian White,

1
@BrianWhite Il fatto divertente, quando proponevo di deprecare questa funzionalità , non riuscivo a trovare alcuna prova che fosse mai stato ufficialmente incoraggiato e solo le versioni beta di PHP 3.0 includevano il comportamento senza preavviso, quindi sembra essere retrocompatibile con una funzionalità che era mai rilasciato. Ad ogni modo, andrà in PHP 8.0, ogni volta che succede.
IMSoP

77

Il messaggio di errore è dovuto al fatto sfortunato che PHP dichiarerà implicitamente un token sconosciuto come una stringa costante con lo stesso nome.

Cioè, sta cercando di interpretare questo (notare le virgolette mancanti):

$_POST[department]

L'unico modo valido per definire questa sintassi in PHP è se in precedenza fosse stata departmentdefinita una costante . Così tristemente, piuttosto che morire con un errore fatale a questo punto, emette questo Avviso e agisce come se fosse stata definita una costante con lo stesso nome e valore:

// Implicit declaration of constant called department with value 'department'
define('department', 'department');  

Esistono vari modi per ottenere questo messaggio di errore, ma hanno tutti la stessa causa principale: un token che potrebbe essere una costante.

Citazioni mancanti nelle stringhe: $my_array[bad_key]

Questo è il problema nel tuo caso, ed è perché hai chiavi di array di stringhe che non sono state citate. Correggere le chiavi di stringa risolverà il bug:

Modificare:

$department = mysql_real_escape_string($_POST[department]);
...(etc)...

Per:

$department = mysql_real_escape_string($_POST['department']);
...(etc)...

Segno di dollaro mancante variabile: var_without_dollar

Un altro motivo per cui potresti visualizzare questo messaggio di errore è se si interrompe $da una variabile o $this->da un membro. Ad esempio, uno dei seguenti potrebbe causare un messaggio di errore simile:

my_local;   // should be $my_local
my_member;  // should be $this->my_member

Carattere non valido nel nome della variabile: $bad-variable-name

Un problema simile ma più sottile può risultare se si tenta di utilizzare un carattere non consentito in un nome di variabile: un trattino ( -) anziché un trattino basso _sarebbe un caso comune.

Ad esempio, questo è OK, poiché i caratteri di sottolineatura sono consentiti nei nomi delle variabili :

if (123 === $my_var) {
  do_something();
}

Ma questo non è:

if (123 === $my-var) {
  do_something();
}

Sarà interpretato come questo:

if (123 === $my - var) {  // variable $my minus constant 'var'
  do_something();
}

Facendo riferimento a una costante di classe senza specificare l'ambito della classe

Per fare riferimento a una costante di classe è necessario specificare l'ambito della classe con ::, se lo si perde PHP penserà che si sta parlando di un globale define().

Per esempio:

class MyClass {
  const MY_CONST = 123;

  public function my_method() {
    return self::MY_CONST;  // This is fine
  }


  public function my_method() {
    return MyClass::MY_CONST;  // This is fine
  }

  public function my_bad_method() {
    return MY_CONST;  // BUG - need to specify class scope
  }
}

Utilizzo di una costante non definita in questa versione di PHP o definita in un'estensione non installata

Esistono alcune costanti definite dal sistema che esistono solo nelle versioni più recenti di PHP, ad esempio le costanti delle opzioni di modalità per round()tali PHP_ROUND_HALF_DOWNesistono solo in PHP 5.3 o versioni successive.

Quindi se hai provato a usare questa funzione in PHP 5.2, dì:

$rounded = round($my_var, 0, PHP_ROUND_HALF_DOWN);

Riceverai questo messaggio di errore:

Uso della costante non definita PHP_ROUND_HALF_DOWN - presupposto 'PHP_ROUND_HALF_DOWN' Avviso (2): conteggio parametri errato per round ()


Grazie per la condivisione. Ho perso la self::parte. Sta lavorando adesso.
moreirapontocom,

Senza dubbio, questa risposta è più completa di altre e merita il miglior badge di risposta! Mi mancava troppo lo Scope di classe e finivo per ottenere alcune preziose informazioni per il futuro. Grazie John!
Harish ST

6

probabilmente hai dimenticato di usare "".

Per esempio:

$_array[text] = $_var;

cambia in:

$_array["text"] = $_var;

3

Ti sei perso mettendo virgolette singole intorno alle chiavi dell'array:

$ _POST [email]

dovrebbe essere:

$ _POST [ 'email']


Dovrebbe essere $ _POST ['email'];
Ibnul Quayum,

1

Il modo corretto di utilizzare le variabili post è

<?php

$department = $_POST['department'];

?>

Usa virgoletta singola (')


1
<?php 
  ${test}="test information";
  echo $test;
?>

Avviso: utilizzo di test costante non definito - assunto 'test' in D: \ xampp \ htdocs \ sp \ test \ envoirnmentVariables.php sulla riga 3 informazioni sul test


1

Inserisci virgolette singole.

Esempio

$department = mysql_real_escape_string($_POST['department']);
$name = mysql_real_escape_string($_POST['name']);
$email = mysql_real_escape_string($_POST['email']);
$message = mysql_real_escape_string($_POST['message']); 

0

Non sono sicuro che ci sia qualche differenza sto usando l'accenditore di codice e io uso "" per i nomi e funziona benissimo.

$department = mysql_real_escape_string($_POST["department"]);
$name = mysql_real_escape_string($_POST["name"]);
$email = mysql_real_escape_string($_POST["email"]);
$message = mysql_real_escape_string($_POST["message"]);

Saluti,

Jorge.


1
In questo caso non c'è differenza tra virgolette singole e doppie.
Robbie Averill,

1
@RobbieAverill mentre in questo caso in realtà non esiste - poiché le stringhe con virgolette singole visualizzano le cose così come sono dove le stringhe con virgolette doppie analizzano i caratteri di escape e valutano le variabili, è consigliabile utilizzare stringhe con virgolette singole in questo scenario.
Frankie,

0

Sembra che le costanti di recupero predefinite siano andate via con l'estensione MySQL, quindi dobbiamo aggiungerle prima della prima funzione ...

// costanti di recupero predefinite

define('MYSQL_BOTH',MYSQLI_BOTH);
define('MYSQL_NUM',MYSQLI_NUM);
define('MYSQL_ASSOC',MYSQLI_ASSOC);

Ho provato e ci sono riuscito.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.