Следует ли заключать в кавычки JSON-кодированные числа из базы данных? - PullRequest
0 голосов
/ 23 марта 2011

У меня есть следующий код:

$stmt = $db->prepare("SELECT LATITUDE, LONGITUDE FROM NODEGEOLOCATION WHERE NODEID = $i");
$stmt->execute();
$path[] = $stmt->fetch(PDO::FETCH_ASSOC);

, и я использую json_encode, чтобы преобразовать его в формат JSON.Однако я получаю следующий код JSON:

[{"route":[{"LATITUDE":"32.224519","LONGITUDE":"-110.947325"},{"LATITUDE":"32.227820","LONGITUDE":"-110.947293"},{"LATITUDE":"32.227843","LONGITUDE":"-110.943865"},{"LATITUDE":"32.230618","LONGITUDE":"-110.943919"},{"LATITUDE":"32.231755","LONGITUDE":"-110.943927"},{"LATITUDE":"32.233836","LONGITUDE":"-110.943963"},{"LATITUDE":"32.233850","LONGITUDE":"-110.946061"},{"LATITUDE":"32.236035","LONGITUDE":"-110.946061"},{"LATITUDE":"32.235993","LONGITUDE":"-110.948083"},{"LATITUDE":"32.235977","LONGITUDE":"-110.952433"}]

Я не хочу, чтобы значения LATITUDE и LONGITUDE были заключены в кавычки.Это вообще возможно?

Ответы [ 2 ]

2 голосов
/ 23 марта 2011

Похоже, что PDO всегда возвращает результаты базы данных в виде строк, даже если они являются числами или числами с плавающей запятой.

JSON-кодировщик PHP не выполняет никакого анализа типов : если значение содержится в строке PHP, оно помещается в кавычки, даже если оно может быть представлено как целое число или число с плавающей запятой.

С этим можно справиться двумя способами.

  1. Перед использованием json_encode.
  2. Измените потребителя JSON для приведения значения в число с плавающей точкой, прежде чем работать с ним.

Вот пример автоматического приведения на основе getColumnMeta. Сначала давайте создадим фиктивную базу данных и вставим некоторые данные.

php > $pdo = new PDO('sqlite::memory:');
php > $pdo->exec('create table foo(a integer, b float, c text)');
php > $sh = $pdo->prepare('insert into foo(a, b, c) values(?, ?, ?)');
php > $sh->execute(array(1, 2.2, 'Three'));
php > $sh->execute(array(4, 5.55, 'Six'));
php > $sh->execute(array(7, 88.888, 'Nine'));

Теперь мы докажем, что данные есть, для нашей демонстрации:

php > $sh = $pdo->prepare('select * from foo where a = 4');
php > $sh->execute();
php > $row = $sh->fetch(PDO::FETCH_ASSOC);
php > var_dump($row);
array(3) {
  ["a"]=>
  string(1) "4"
  ["b"]=>
  string(4) "5.55"
  ["c"]=>
  string(3) "Six"
}

Посмотрим, что скажет нам PDO о первом столбце.

php > print_r($sh->getColumnMeta(0));
Array
(
    [native_type] => integer
    [sqlite:decl_type] => integer
    [flags] => Array
        (
        )

    [name] => a
    [len] => 4294967295
    [precision] => 0
    [pdo_type] => 2
)

Красивая. Я сделал это и для столбцов 1 и 2, которые возвращали «double» и «string» соответственно. Теперь давайте создадим карту имени столбца для ввода:

php > $cols = count($row);
php > $col_types = array(); 
php > while($cols-- > 0) { 
          $col_info = $sh->getColumnMeta($cols);
          $col_types[ $col_info['name'] ] = $col_info['native_type']; 
      }
php > print_r($col_types);
Array
(
    [c] => string
    [b] => double
    [a] => integer
)

Да, все наоборот, не имеет значения! Теперь давайте преобразуем наш ряд.

php > foreach($row as $k => $v) {
          if($col_types[$k] == 'double')
              $row[$k] = (float)$v;
          if($col_types[$k] == 'integer')
              $row[$k] = (int)$v;
      }
php > var_dump($row);
array(3) {
  ["a"]=>
  int(4)
  ["b"]=>
  float(5.55)
  ["c"]=>
  string(3) "Six"
}
php > echo json_encode($row);
{"a":4,"b":5.55,"c":"Six"}

Тад! Вы, вероятно, захотите обернуть это в удобный метод, это немного сложно сделать каждый раз вручную. Я мог бы также использовать columnCount , чтобы получить количество столбцов в наборе результатов, а не считать $row.


много перебить? Вот пример непроверенный , который нацелен на конкретные имена столбцов и строит массив хэшей вручную в процессе.

$results = array();
$convert_columns = array( 'b' );
$sh = $pdo->prepare('select * from foo where a = 1');
$sh->execute();
while($row = $sh->fetch(PDO::FETCH_ASSOC)) {
    foreach($convert_columns as $colname)
        $row[$colname] = (float)$row[$colname];
    $results[] = $row;
}
2 голосов
/ 23 марта 2011

Я полагаю, это зависит от их типа в базе данных.

Если они являются вархивами или строками в базе данных, они рассматриваются как строки.

Если они FLOAT DOUBLE, у них не должно быть кавычек.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...