2009-07-13 4 views
1

Ich habe ein assoziatives Array, auf das ich möglicherweise numerisch zugreifen muss (z. B. den Wert des 5. Schlüssels erhalten).Array mit assoziativen Werten, auf die numerisch zugegriffen wird

$data = array(
    'one' => 'something', 
    'two' => 'else', 
    'three' => 'completely' 
) ; 

Ich muss in der Lage sein zu tun:

$data['one'] 

und

$data[0] 

den gleichen Wert bekommen, 'etwas'.

Mein erster Gedanke ist es, eine Wrapper-Klasse zu erstellen, die Arrayaccess mit offsetGet implementiert() Code zu sehen, ob der Schlüssel numerisch ist und entsprechend handeln, mit array_values:

class MixedArray implements ArrayAccess { 

    protected $_array = array(); 

    public function __construct($data) { 
     $this->_array = $data; 
    } 

    public function offsetExists($offset) { 
     return isset($this->_array[$offset]); 
    } 

    public function offsetGet($offset) { 
     if (is_numeric($offset) || !isset($this->_array[$offset])) { 
      $values = array_values($this->_array) ; 
      if (!isset($values[$offset])) { 
       return false ; 
      } 
      return $values[$offset] ; 
     }     
     return $this->_array[$offset]; 
    } 

    public function offsetSet($offset, $value) { 
     return $this->_array[$offset] = $value; 
    } 

    public function offsetUnset($offset) { 
     unset($this->_array[$offset]); 
    }  

} 

Ich frage mich, ob es ‚isn t irgendwelche eingebauten in PHP, um dies zu tun. Ich würde lieber native Funktionen verwenden, aber bisher habe ich nichts gesehen, was das tut.

Irgendwelche Ideen?

Danke,
Fanis

+0

Ich habe gerade festgestellt, dass ich dies nicht aktualisiert hatte, seitdem ich es fragte. Ich endete mit dem, was ich in der Frage geschrieben habe, aber leicht optimiert, um die numerischen Indizes in einer Klassenvariablen zu halten, nachdem sie zuerst mit array_values ​​() gefunden wurden. – Fanis

Antwort

0

i bemerkt, dass Sie erwähnt es ist ein Nur-Lese-Datenbank Ergebnis

gesetzt

, wenn Sie mysql verwenden, dann Sie mit beiden assoziativen und numerischen Tasten

so etwas wie dieses

$result = mysql_query($sql); 
$data = mysql_fetch_array($result); 

mysql_fetch_array gibt ein Array tun könnte

http://nz.php.net/manual/en/function.mysql-fetch-array.php

+0

Ah, sehr guter Fang. Das hatte ich vergessen. Ich benutze jedoch PEAR :: DB, die diese Option nicht öffentlich verfügbar zu machen scheint. Ich denke, ich könnte einfach in PEAR/DB/mysql eintauchen.php :: fetchInto() und ändere es, um MYSQL_BOTH zu verwenden, aber ich würde es lieber nicht so hacken :) Noch gabst du mir etwas zum Nachdenken, danke – Fanis

4
how about this 

$data = array(
    'one' => 'something', 
    'two' => 'else', 
    'three' => 'completely' 
) ; 

then 
$keys = array_keys($data); 

Then 
$key = $keys[$index_you_want]; 

Then 
echo $data[$key]; 
+0

Richtig, aber ich weiß nicht im Voraus, ob ich numerisch oder assoziativ bin. Ich muss beide für jemanden arbeiten, der meinen Array-Wrapper benutzt. – Fanis

+0

sollte es für beide funktionieren. – TigerTiger

1

Es ist keine eingebaute Möglichkeit, dies zu tun ist.

Wenn es eine einmalige Sache, die Sie so etwas wie verwenden:

$array = array_merge($array, array_values($array)); 

Dieses Update wird nicht, wie Sie wenn neue Elemente zum Array hinzufügen.

+0

Dies ist ziemlich readonly (Datenbank Ergebnismenge), so denke ich, könnte das funktionieren. Es würde jedoch mehr Speicher auffressen, was in großen Mengen unerwünscht sein könnte. Ich werde es im Hinterkopf behalten, da es einfach der schnellste Weg für kleinere Sätze sein kann, anstatt 2 Lagen Wrapper drüber zu haben – Fanis

0

Manchmal ist es einfacher zu überprüfen, ob Sie einen assoziativen Schlüssel oder eine n index mit is_int()

if(is_int($key)) 
    return current(array_slice($data, $key, 1)); 
else 
    return $data[$key]; 
+0

Ich mag deine array_slice Option, danke. Aber ich brauche das für jeden, der meinen Code benutzt, transparent zu sein. Sie können auf das Array numerisch oder über einen Zeichenfolgenschlüssel zugreifen. Ich experimentiere mit einem ArrayAccess-Wrapper. Bis jetzt sieht es gut aus, obwohl es ein paar Optimierungen zu machen gibt, wie zum Beispiel an native Funktionen, die Arrays erwarten (zB array_rand()), aber ich komme dorthin. – Fanis