2009-09-25 13 views
7

Sono sicuro che c'è di meglio. Qualsiasi aiuto sarà molto apprezzato.Argomenti funzionali opzionali PHP con array. Come codice/modo migliore per codificare?

Voglio passare una matrice a una funzione php che contiene l'argomento e tutti gli argomenti sono facoltativi. Sto usando l'accenditore del codice e non sono affatto un esperto. Qui di seguito è quello che ho usato finora:

function addLinkPost($postDetailArray) { 

    if (isset($postDetailArray['title'])) { 
     $title = $postDetailArray['title']; } 
    else { 
     $title = "Error: No Title"; 
    } 

    if (isset($postDetailArray['url'])) { 
     $url  = $postDetailArray['url']; 
    } else { 
     $url  = "no url"; 
    } 
    if (isset($postDetailArray['caption'])) { 
     $caption = $postDetailArray['caption']; 
    } else { 
     $caption = ""; 
    } 
    if (isset($postDetailArray['publish'])) { 
     $publish = $postDetailArray['publish']; 
    } else { 
     $publish = TRUE; 
    } 
    if (isset($postDetailArray['postdate'])) { 
     $postdate = $postDetailArray['postdate']; 
    } else { 
     $postdate = "NOW()"; 
    } 
    if (isset($postDetailArray['tagString'])) { 
     $tagString = $postDetailArray['tagString']; 
    } else { 
     $tagString = ""; 
    } 

risposta

10

Si potrebbe fare così:

function addLinkPost(array $postDetailArray) 
{ 
    $fields = array(
     'key' => 'default value', 
     'title' => 'Error: No Title', 
    ); 

    foreach ($fields as $key => $default) { 
     $$key = isset($postDetailArray[$key]) ? $postDetailArray[$key] : $default; 
    } 
} 

È sufficiente modificare l'array $ campi con la chiave e il suo valore di default.

+0

Dovresti stare un po 'attento a fare cose del genere, specialmente se i dati sono forniti dall'utente, perché è simile a register_globals. –

+0

@Tom Anche se personalmente l'avrei implementato usando una matrice per memorizzare i valori in contrasto con la variabile di funzione locale che usava nella sua domanda e ho usato nella mia risposta, si poteva implementare un rapido controllo nel ciclo foreach per ignorare qualsiasi chiavi fornite che non sono nell'array $ fields – Inspire

+0

In realtà, a mio parere, il mio esempio esegue iterazioni sull'array $ fields anziché su $ postDetailArray, quindi il controllo delle chiavi non sarebbe necessario. – Inspire

0

Penso che l'esempio va bene. Non penso che ci sia molto più ottimizzazione da fare qui, a parte forse lasciare poche parentesi.

opzionalmente, è possibile controllare il funzionamento estratto in PHP

0

ne dite:

function getdefault($value, $default = null) { 
    return isset($value) ? $value : $default; 
} 

function addLinkPost($postDetailArray) { 
    $title = getdefault($postDetailArray['title'], 'Error: No Title'); 
    $url = getdefault($postDetailArray['url'], 'no url'); 
    $caption = getdefault($postDetailArray['caption'], ''); 
    $publish = getdefault($postDetailArray['publish'], TRUE); 
    $postdate = getdefault($postDetailArray['postdate'], 'NOW()'); 
    $tagString = getdefault($postDetailArray['tagString'], ''); 
} 

o in alternativa:

$defaults = array(
    'title' => 'Error: No Title', 
    'url' => 'no url', 
    'caption' => '', 
    'publish' => TRUE, 
    'postdate' => 'NOW()', 
    'tagString' => '', 
); 

function addLinkPost($postDetailArray) { 
    global $defaults; 
    foreach ($defaults as $k => $v) { 
    $$k = isset($postDetailArray[$k]) ? $postDetailArray[$k] : $v; 
    } 
} 

Con quello avvertendo che se si dispone di una chiave di serie di ' valori predefiniti 'in $defaults, sovrascriverà il globale $defaults.

+0

That ('$ postDetailArray [ 'title']') avrebbe emesso un avviso. –

4

L'utilizzo dell'array come argomento è una buona idea in questo caso. Tuttavia, è possibile semplificare un po 'il codice nella funzione utilizzando l'operatore ternario (http://dk.php.net/ternary):

$ title = isset ($ postDetailArray [' title '])? $ postDetailArray ['title']: 'Errore: Nessun titolo';

Si potrebbe semplificare ancora di più nel modo seguente:

function addLinkPost($data) { 

$arguments = array('title', 'url', 'caption', 'publish', 'postdate', 'tagString'); 

foreach ($arguments as $value) { 
    $$value = isset($data[$value]) ? $data[$value] : 'Error: No '.$value; 
} 

}

+0

Appena notato che non dovrebbe essere 'Errore: No ...' per tutte le opzioni, ma ancora ... Hai avuto l'idea. – Jonas

0

Prova questa:

function addLinkPost($postDetailArray) { 

    foreach($array as $key=>$value){ 
    $$key = (isset($value) && !empty($value)) ? $value : ('no '.$key); 
    } 
    //all keys are available as variables 
    var_dump($url); var_dump($publish); //etc 
} 
0

Si potrebbe fare tutti gli elementi dei parametri di matrice della funzione. Controlla se il primo è un array nella funzione e, in tal caso, estrai l'array.

function addLinkPost($title = null, $url = null, $caption = null, $publish = null, $postDate = null, $tagString = null) 
{ 
     if(is_array($title)) { 
      extract($title); 
     } 

     .... 
} 

Forse questo rende il codice un po 'più chiaro.

27

È possibile utilizzare un array di valori predefiniti e quindi unire l'array di argomenti con i valori predefiniti. I valori predefiniti verranno sovrascritti se compaiono nell'array degli argomenti. Un semplice esempio:

$defaults = array(
    'foo' => 'aaa', 
    'bar' => 'bbb', 
    'baz' => 'ccc', 
); 

$options = array(
    'foo' => 'ddd', 
); 


$merged = array_merge($defaults, $options); 

print_r($merged); 

/* 

Array 
(
    [foo] => ddd 
    [bar] => bbb 
    [baz] => ccc 
) 

*/ 

Nel tuo caso, che sarebbe:

function addLinkPost($postDetailArray) { 
    static $defaults = array(
     'title'  => 'Error: No Title', 
     'url'  => 'no url', 
     'caption' => '', 
     'publish' => true, 
     'postdate' => 'NOW()', 
     'tagString' => '', 
    ); 

    $merged = array_merge($defaults, $postDetailArray); 

    $title  = $merged['title']; 
    $url  = $merged['url']; 
    $caption = $merged['caption']; 
    $publish = $merged['publish']; 
    $postdate = $merged['postdate']; 
    $tagString = $merged['$tagString']; 
} 
+0

Questo è il modo per farlo. Ottieni il risultato desiderato e ottieni un riepilogo molto leggibile dei valori predefiniti. È essenzialmente lasciare che PHP faccia per te invece di andare in loop, da solo. PHP offre così tante meravigliose funzioni di array, che aborro in loop su un array - ogni volta che vedo il looping di un array, sento qualcosa che probabilmente può essere sostituito da funzioni native dell'array. – grantwparks

+0

Accetto - questo è di gran lunga il modo più leggibile per farlo. Meno LOC non è sempre meglio. – calumbrodie

+0

Elegante! Si noti, tuttavia, che l'uso di una matrice "unita" separata non è strettamente necessario. Sto aggiungendo il seguente come miglioramento del codice esistente: $ argsR = array_merge ($ defaultsR, $ argsR; ($ argsR è la matrice di argomenti della funzione esistente passata ed elaborata dalla funzione esistente). –

Problemi correlati