2013-04-13 27 views
2

例子:有什麼辦法可以通過PHP中的表名分隔MySQL查詢結果嗎?

SELECT chapter.id, book.title, book.author FROM chapter 
INNER JOIN book ON (chapter.book = book.id) 

獲取該查詢後,我希望得到的東西是這樣的:

Array 
(
    [0] => Array 
     (
      [chapter] => Array 
       (
        [id] => 1 
       ) 

      [book] => Array 
       (
        [title] => Lorem Ipsum 
        [author] => John Doe 
       ) 

     ) 

) 

更重要的是,stdClass的對象。

那麼,經過一段時間的搜索和工作後,我發現了一種通過解析SQL語句來執行我想要的操作的方法,但這對我的問題來說確實不是一個好的解決方案。

我有這方面的具體原因,一個解決方案將是我的項目的一個很大的好處。雖然我不認爲有這樣做的更簡單的方法...

+0

在遍歷結果集的所有行的循環中,您可以輕鬆地以所需的模式創建該新陣列 –

+0

大多數數據庫客戶端庫都提供元數據,例如,將結果列歸屬到哪個表中:http://www.php.net/mysqli-result.fetch-field-direct.php http://www.php.net/mysqli-result.fetch-fields.php http ://www.php.net/pdostatement.getcolumnmeta.php –

+0

謝謝@ M8R-1jmw5r,我認爲'mysqli_fetch_field_direct'可能是解決方案...我會試試 – DMF

回答

0
$query   = $myPdoInstance->prepare('SELECT lorem FROM ipsum...'); 
$metaData  = array(); 
$data   = new stdClass; 
$i    = 0; 
$tablesIdField = 'id'; 

$query->execute(); 

while ($columnsMeta = $query->getColumnMeta($i++)) { 
    $metaData[] = $columnsMeta; 
} 

foreach ($query->fetch(PDO::FETCH_NUM) as $key => $columnValue) { 

    $currentTable = $meta[$key]['table']; 

    if (!isset($data->{$currentTable})) { 
     $data->{$currentTable} = new stdClass; 
    } elseif (!is_object($data->{$currentTable})) { 
     $prev         = $data->{$currentTable}; 
     $data->{$currentTable}     = new stdClass; 
     $data->{$currentTable}->{$tablesIdField} = $prev; 
    } 

    $data->{$currentTable}->{$meta[$key]['name']} = $columnValue; 
} 

這是什麼,我做了一個很簡單的例子。這是我的項目的一個很好的解決方案。 我在我的項目中使用的代碼太複雜了,並且我實現了類來將它發佈到此處。

因此,如果在這個例子中有任何語法錯誤,我很抱歉!

1

一種方法是命名(別名)的結果集的列以這樣一種方式,您的PHP代碼知道在哪裏「文件「他們,例如與表和列的分裂與:

SELECT chapter.id as `chapter:id`, book.title as `book:title`, book.author as `book:author` ... 

然後從PDO檢索結果時/庫MySQLi,可以拆分所產生的密鑰知道在哪裏可以存儲你的數據:

$formatted_row = array(); 
foreach ($db_row as $column_alias => $value) 
{ 
    list($table, $column) = explode(':', $column_alias); 
    $formatted_row[$table][$column] = $value; 
} 
+0

感謝您的回答,但這並不像我想要的那樣實用。 我正在使用'PDOStatement :: getColumnMeta'並收集所有元,然後構建對象。它比我想象的完美和快速! – DMF

+0

@DMF對列元數據的一個優點是你可以選擇原始列以外的東西(例如'count(*)'或以特定方式格式化的日期)。無論這是一個很大的考慮因素取決於你。 – IMSoP

+0

+1:無論如何,這將是我會提出的另一種選擇。我曾考慮過使用'_'作爲分隔符。對於爆炸,您可以添加第二個參數。 –

1

fetch_fields()功能會給你你需要的信息。該腳本

<?php 
$sql = " 
SELECT u.user, h.db, RAND() x FROM mysql.user u 
LEFT JOIN mysql.host h ON h.host = u.host 
"; 
$conn = new mysqli('localhost', 'root', '', 'mysql'); 
$stmt = $conn->query($sql); 
$fields = $stmt->fetch_fields(); 
print_r($fields); 

產生以下輸出:

Array(
    [0] => stdClass Object(
      [name] => user 
      [orgname] => User 
      [table] => u 
      [orgtable] => user 
      [def] => 
      [db] => mysql 
      ... 
     ) 
    [1] => stdClass Object(
      [name] => db 
      [orgname] => Db 
      [table] => h 
      [orgtable] => host 
      [def] => 
      [db] => mysql 
      ... 
     ) 
    [2] => stdClass Object(
      [name] => x 
      [orgname] => 
      [table] => 
      [orgtable] => 
      [def] => 
      [db] => 
      ... 
     ) 
) 

,所以你可以使用dborgtable字段,以確定每個字段來自哪一個表格。

+0

是的......我剛剛發現PDO的'getColumnMeta'不會給你這個'orgtable'(=「原始表」)和'orgname'(=「原始列名」)信息,根據你的要求,確實非常有用。 –

相關問題