Domanda

Contesto

  • PHP 5.3.x

Panoramica

Dopo aver fatto un codice-review con un socio che usa sia PHP e Ruby di routine, una sfida divertente, salì sul interpolazione stringa in php rispetto al rubino.

Domanda

Si supponga color = "orange";

Rubino:

puts("My favorite color is #{color.downcase() + 'ish'} -- at least for now.");

PHP:

print("My favorite color is {strtolower( $color ) + 'ish'} -- at least for now.");

Challenge:? chiunque può specificare un modo per ottenere la versione di PHP si comporta come Ruby

Caveat

Questa sfida è inteso come un esercizio divertente con il vincolo di utilizzare solo PHP dritto. Questo non è destinato a seri progetti di PHP. Per i seri progetti di PHP, lo sviluppatore consiglia di considerare le biblioteche addon, come TWIG .

È stato utile?

Soluzione

Non è possibile chiamare funzioni semplici all'interno delle stringhe del genere, ma è possibile convincere il parser a fare cose strane:

<?php
print "{$a->b()}"; // Works

//Parse error: syntax error, unexpected '(' in Command line code on line 1
print "${time()}";

print "${$a=time()} $a"; // Also works: prints "1234380996"
?>

Fino a quando si vede una variabile valido alla partenza, sarà andare avanti e interpolare un intero dichiarazione senza lamentarsi.

Per chi stesse chiedendo, sì, questo funziona anche ...

<?php
print "${$a or print shell_exec('ls')}";
?>

Altri suggerimenti

Stai vicino, è possibile incorporare le variabili nelle stringhe, ma non chiamate di funzione.

Io uso printf() (e sprintf()) per questo, che è un wrapper sottile intorno alla funzione C con lo stesso nome:

printf('My favorite color is %sish -- at least for now.', strtolower( $color ));

Vedere che %s lì dentro? Questo è il segnaposto per il tipo di dati stringa che si sta passando come il 2 ° argomento.

sprintf() funziona allo stesso modo, ma restituisce la stringa formattata invece di print'ing esso.

Le uniche altre opzioni sono:

A. Svolgere la funzione chiamate prima e assegnando il risultato finale alla variabile:

$color = strtolower( $color );
print("My favorite color is {$color}ish -- at least for now.");

B. Utilizzando la concatenazione, che è un po 'brutto IMO:

print('My favorite color is ' . strtolower( $color ) . 'ish -- at least for now.');

Avrete notato il mio uso di virgolette singole (zecche aka) ei doppi apici.

In PHP, letterali tra virgolette vengono analizzati per le variabili, come si vede in "A" di cui sopra.

I letterali all'interno di apici non vengono analizzati. A causa di questo, sono più veloci. Si dovrebbe, di regola, usare solo virgolette intorno letterali quando c'è una variabile da analizzare.

'My favorite color is ' . strtolower( $color ) . 'ish-- at least for now.'

Non credo che PHP supporta le espressioni piene interpolati in stringhe. Stato un po 'da quando ho fatto alcun PHP però.

Se questo è qualcosa va ....

class ColorIsh {
    var $color;

    function __constructor($color) { $this->color = $color; }
    function __get($prop) {
        if ($prop == 'ish') {
            // code here fixing suffix if needed
            return strtolower($this->color) . 'ish';
        }
        return '';
    }
    function __set($prop) {}
}

$color = new ColorIsh("orange");
$str = "My favorite color is $color->ish -- at least for now.";

E la versione avanzata iper

class ColorIsh {
    private $color;

    function __constructor($color) {$this->color = $color; }
    function __get($prop) {
        if ($prop == 'color') 
            return $this->color;
        if ($prop == 'ish')
            return isset($this->ish) ? $this->ish : $this->color . 'ish';
        return false;
    }
    function __set($prop, $value) {
        if ($prop == 'color') { $this->color = $value; unset($this->ish); }
        if ($prop == 'ish') { $this->ish = $value; }
    }
}

$color = new ColorIsh('orange');
$color->ish = 'orangish';
print "The color is kinda $color->ish";
$color->color = 'green';
print "The color is kinda $color->ish";

output:
The color is kinda orangish.
The color is kinda greenish.

Non è così bella, ma è possibile utilizzare una funzione anonima.

$e = function($val) { return $val; };
$foo = 'foo';
echo "Uppercase foo = {$e(strtoupper($foo))}";

I miei progetti hanno di solito una funzione di supporto che restituisce la funzione anonima sopra, in modo che non ha bisogno di essere ricreato ogni volta.

function returner() {
    static $returner;

    if (!$returner) {
        $returner = function($val) {
            return $val;
        };
    }

    return $returner;
}

$e = returner();

Non è possibile. Ma se proprio insistete, si può sempre creare una classe String con un'interfaccia fluida ... ma questo è matto:)

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top