Domanda

Quindi sto provando a creare uno script che antepone automagicamente nomi di colonna validi con il prefisso di tabella appropriato (ad es. " t. " o " r. ")

$t_columns = array('id', 'name', 'label');
$r_columns = array('related_value');

INPUT:

id > 1 AND (name = 'Hello' OR label IN ('World', 'Planet name AND label')) AND (related_value > 1 AND related_value < 50)

USCITA:

t.id > 1 AND (t.name = 'Hello' OR t.label IN ('World', 'Planet name AND label')) AND (r.related_value > 1 AND r.related_value < 50)

Nota come non puoi fare un normale str_replace . Quale sarebbe il codice più semplice (sto indovinando preg_replace ) per garantire che tutti i nomi delle tabelle siano anteposti correttamente?

È stato utile?

Soluzione

Questo può essere fatto in molti modi e anche usando regex. Personalmente userei un approccio array. Prima di tutto, definirei la tabella dei mangling in questo modo:

$table = array(
    'id' => 't.id',
    'name' => 't.name',
    'label' => 't.label',
    'related_value' => 'r.related_value'
);

Questo renderà molto più facile la chiamata str_replace ():

function mangling(&$v, $k, $table)
{
    if (($k & 1) == 0)
        $v = str_replace(array_keys($table), array_values($table), $v);
}

$spans = explode("'", ' ' . $input);
array_walk($spans, 'mangling', $table);
$output = implode("'", $spans);

Altri suggerimenti

Dopo qualche secondo di riflessione, ecco come lo affronterei:

Cammina attraverso la stringa, carattere per carattere, cercando virgolette singole, ma saltando i caratteri di escape. La roba tra due virgolette singole senza escape (ovvero le stringhe) verrebbe sostituita con un token univoco e inserita in un array associativo, con quel token come chiave e la stringa originale come valore.

Ora che abbiamo le stringhe di mezzo, fai un str_replace () (o preg_replace () , se insisti) per i nomi delle colonne conosciute. Probabilmente costruirei i nomi delle colonne in un array associativo, con l'alias della tabella come chiave e il valore come un array enumerato contenente i nomi delle colonne. In questo modo, la sostituzione potrebbe essere automatizzata.

Dopo aver inserito i nomi delle tabelle, basta fare un str_replace () per i token, per sostituire le stringhe originali al loro posto e il gioco è fatto.

Sono sicuro che qualcuno potrebbe lanciare un regexp super fantastico (e probabilmente vicino a non mantenibile) per fare tutto questo in un colpo solo. Ma preferisco usare regexps solo in situazioni in cui le espressioni regolari sono in realtà lo strumento giusto, non dove un CFL sarebbe più adatto.

Non so se un'espressione regolare sia una buona idea qui. Direi che varrebbe la minima quantità di maggiore complessità computazionale per eseguire da soli la validazione in PHP. Quindi, se il tuo database richiede modifiche, non dovrai toglierti i capelli preoccupandoti di come aumentare la robustezza della tua espressione regolare.

Come disse una volta Jamie Zawinski, " Alcune persone, di fronte a un problema, pensano "Lo so, userò espressioni regolari". Ora hanno due problemi. & Quot;

In termini di creazione di un flusso di lavoro che assicurerà che tu stia lavorando sul database giusto, prenderei in considerazione un approccio orientato agli oggetti. Le classi per le tabelle T e R possono essere istanziazioni secondarie di una classe modello responsabile della creazione dell'oggetto di tipo tabella corretto utilizzando la logica condizionale all'interno dello stesso metodo, anziché una regex.

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