Chaves em cadeia no PHP

Respostas:

281

Esta é a sintaxe complexa (curvada) para interpolação de cadeias. Do manual:

Sintaxe complexa (ondulada)

Isso não é chamado complexo porque a sintaxe é complexa, mas porque permite o uso de expressões complexas.

Qualquer variável escalar, elemento de matriz ou propriedade de objeto com uma representação de cadeia de caracteres pode ser incluída por meio desta sintaxe. Simplesmente escreva a expressão da mesma maneira que apareceria fora da string e, em seguida, envolva-a com {e }. Como {não pode ser escapado, essa sintaxe será reconhecida apenas quando o $seguinte for imediatamente {. Use {\$para obter um literal {$. Alguns exemplos para deixar claro:

<?php
// Show all errors
error_reporting(E_ALL);

$great = 'fantastic';

// Won't work, outputs: This is { fantastic}
echo "This is { $great}";

// Works, outputs: This is fantastic
echo "This is {$great}";
echo "This is ${great}";

// Works
echo "This square is {$square->width}00 centimeters broad."; 


// Works, quoted keys only work using the curly brace syntax
echo "This works: {$arr['key']}";


// Works
echo "This works: {$arr[4][3]}";

// This is wrong for the same reason as $foo[bar] is wrong  outside a string.
// In other words, it will still work, but only because PHP first looks for a
// constant named foo; an error of level E_NOTICE (undefined constant) will be
// thrown.
echo "This is wrong: {$arr[foo][3]}"; 

// Works. When using multi-dimensional arrays, always use braces around arrays
// when inside of strings
echo "This works: {$arr['foo'][3]}";

// Works.
echo "This works: " . $arr['foo'][3];

echo "This works too: {$obj->values[3]->name}";

echo "This is the value of the var named $name: {${$name}}";

echo "This is the value of the var named by the return value of getName(): {${getName()}}";

echo "This is the value of the var named by the return value of \$object->getName(): {${$object->getName()}}";

// Won't work, outputs: This is the return value of getName(): {getName()}
echo "This is the return value of getName(): {getName()}";
?>

Freqüentemente, essa sintaxe é desnecessária. Por exemplo, isto:

$a = 'abcd';
$out = "$a $a"; // "abcd abcd";

se comporta exatamente da mesma maneira que isto:

$out = "{$a} {$a}"; // same

Portanto, o aparelho não é necessário. Mas isso :

$out = "$aefgh";

, dependendo do seu nível de erro, não funcionará ou produzirá um erro porque não há uma variável nomeada $aefgh; portanto, você precisa:

$out = "${a}efgh"; // or
$out = "{$a}efgh";
cleto
fonte
40
muito anal nitpicking sobre copiar / colar. Se facilita a compreensão / localização, foi uma boa decisão. Com +1 de mim, era exatamente o que eu estava procurando e não o encontrei no manual do PHP - talvez porque eles chamam pelo nome próprio ou o que seja. Mas eu encontrei aqui.
Gabriel Magana
9
Para curvas literais, dobre-as, por exemplo $vars='x:3,y:9'; $json="{{$vars}}";. Graças ao artigo de QiGuang .
22813 Bob Stein
... Ou $out = '$aefgh'; (se você precisa do literalmente $ aefgh)
Roko C. Buljan
Um exemplo interessante de caso de uso é SimpleXMLElement: {}é usado para acessar o próprio nó, por exemplo $element[0]->{0}. Como a propriedade "0" não pode existir, isso será acionado __get/ __setmétodo. Em essência, isso permite uma alternativa ArrayAccesspara o acesso ao índice, por exemplo, 3v4l.org/1F254 .
Gajus
2
Se um conteúdo dentro chaves literais contém variáveis também, em seguida, adicione Curly-chaves para cada variável: $min=1;$max=5; echo ".{{$min},{$max}}"yields .{1,5}(eu tinha problemas saber para onde "double [as chaves] up" mencionada no @ o comentário de BobStein)
Xenos
47

Quanto a mim, os chavetas servem como substitutos da concatenação, são mais rápidos para digitar e o código parece mais limpo. Lembre-se de usar aspas duplas (""), pois seu conteúdo é analisado pelo PHP, porque em aspas simples ('') você obterá o nome literal da variável fornecida:

<?php

 $a = '12345';

// This works:
 echo "qwe{$a}rty"; // qwe12345rty, using braces
 echo "qwe" . $a . "rty"; // qwe12345rty, concatenation used

// Does not work:
 echo 'qwe{$a}rty'; // qwe{$a}rty, single quotes are not parsed
 echo "qwe$arty"; // qwe, because $a became $arty, which is undefined

?>
Kredo900
fonte
1
"o conteúdo deles é analisado pelo PHP" - Isso é enganador. Você não pode simplesmente colocar expressões arbitrárias em PHP dentro da sintaxe de chaves, que é o que eu leio sua citação.
Mark Amery
1
Na IMO, no geral, não é mais rápido digitar entre colchetes. Você deve SHIFTpressionar a tecla para aspas duplas e colchetes. Seria mais rápido, se você usasse estritamente aspas duplas.
Deflime
2
Obrigado por destacar aspas duplas x aspas simples, +1
cameronjonesweb 8/16
Eu usaria em evaluatevez deparse
Cholthi Paul Ttiopic 5/18
17

Exemplo:

$number = 4;
print "You have the {$number}th edition book";
//output: "You have the 4th edition book";

Sem chaves, o PHP tentaria encontrar uma variável chamada $numberth, que não existe!

Obiware
fonte
3

Também achei útil acessar atributos de objetos em que os nomes dos atributos variam de acordo com algum iterador. Por exemplo, usei o padrão abaixo para um conjunto de períodos: hora, dia, mês.

$periods=array('hour', 'day', 'month');
foreach ($periods as $period)
{
    $this->{'value_'.$period}=1;
}

Esse mesmo padrão também pode ser usado para acessar métodos de classe. Apenas crie o nome do método da mesma maneira, usando strings e variáveis ​​de strings.

Você poderia argumentar facilmente usar apenas uma matriz para o armazenamento de valor por período. Se esse aplicativo fosse apenas PHP, eu concordo. Eu uso esse padrão quando os atributos de classe são mapeados para os campos em uma tabela de banco de dados. Embora seja possível armazenar matrizes em um banco de dados usando serialização, é ineficiente e inútil se os campos individuais devem ser indexados. Costumo adicionar uma matriz de nomes de campos, digitados pelo iterador, para o melhor dos dois mundos.

class timevalues
{
                             // Database table values:
    public $value_hour;      // maps to values.value_hour
    public $value_day;       // maps to values.value_day
    public $value_month;     // maps to values.value_month
    public $values=array();

    public function __construct()
    {
        $this->value_hour=0;
        $this->value_day=0;
        $this->value_month=0;
        $this->values=array(
            'hour'=>$this->value_hour,
            'day'=>$this->value_day,
            'month'=>$this->value_month,
        );
    }
}
Ray N. Franklin
fonte
-5

aqui está o código que recebi de um plugin wordpress

$data = $wpdb->get_results("select * from {$wpdb->prefix}download_monitor_files");

Essa é uma técnica realmente útil para formatar seqüências complexas.

user1232972
fonte