【PHP・JSON】json_encodeの使い方・日本語対応とjson_decodeの使い方・連想配列かObjectかの選択

php-json

こんにちはフロントエンドエンジニアのまさにょんです!

今回は、PHPのjson_encode と json_decode の使い方や json_encode 時の日本語対応の方法、json_decode 時の連想配列かObjectかの選択について解説します。

そもそもJSONとは?

JSON(JavaScript Object Notation)とは、データフォーマットの1つで、データの記述方法などが違うプログラム言語同士でデータをやり取りするためのものです。

JSONデータは、その名のとおり「JavaScript の Object の Notation(記法)」で記述されたデータです。

つまり、JavaScriptのObjectの記述方法に則って作られています。

PHPのデータをJSONに変換する json_encode() の使い方

PHPでデータをJSONに変換する場合は、json_encode() を使います。

PHP-Manualの説明は、次のとおりです。

json_encode — 値を JSON 形式にして返す

[ 説明 ]

json_encode(mixed $value, int $flags = 0, int $depth = 512): string|false

与えられた value を JSON 形式にした文字列を返します。

引数が配列やオブジェクトの場合は、JSON 形式に再帰的に変換されます。

変換される値がオブジェクトの場合、 デフォルトでは public としてアクセス可能なプロパティのみが含まれます。

それ以外のやり方で、値を JSON 形式に変換する方法は、 JsonSerializable を実装することで制御できます。

エンコーディングは、flags の指定によって影響を受けます。

さらに、浮動小数点のエンコーディングは、 serialize_precision の値によっても影響を受けます。

[ パラメータ ]

1. value : エンコードする値。 リソース 型以外の任意の型を指定できます。

すべての文字列データは、UTF-8 エンコードされていなければいけません。

2. flags : JSON_UNESCAPED_UNICODEなどの定数のFlag

各定数の意味については JSON 定数のページ に説明があります。

3. depth : 最大の深さを設定します。正の数でなければいけません。

[ 戻り値 ]

成功した場合に、JSON エンコードされた文字列を返します。 失敗した場合に false を返します。

引用元: PHP-Manual: json_encode
<?php

// [ json_encodeとは ]

// 指定した値をJSON形式に変換するには、json_encode関数を使用します。

$gunma_teikoku = ['kiryu', 'maebashi', 'takasaki'];

// 配列をJSON形式に変換する
$gunma_json = json_encode($gunma_teikoku);

echo $gunma_json;
echo "\n";
// ["kiryu","maebashi","takasaki"]

連想配列をjson_encode()するとObjectの構造に変換される

PHPの連想配列は、JSONデータにする時に、Objectの構造に変換されるので注意が必要です。

<?php

// 連想配列を作成
$from_array = [
    'robotama' => 'gunma',
    'robotama-1'=> 'saitama',
    'robotama-2'=> 'tokyo',
    'robotama-3' => 'kanagawa',
    'neo-robotama' => 'okinawa'
];

// 連想配列をJSON形式に変換する
$from_json = json_encode($from_array);

// 連想配列は、JSONエンコードすると、Objectの構造になる!
echo $from_json;
echo "\n";
// {
//   "robotama":"gunma","robotama-1":"saitama","robotama-2":"tokyo",
//   "robotama-3":"kanagawa","neo-robotama":"okinawa"
// }

日本語をjson_encodeするには「JSON_UNESCAPED_UNICODE」Flagを設定する

日本語が含まれる配列をjson_encodeでエンコードすると、日本語が文字コードで表示されてしまいます。

そのため、日本語をjson_encodeする時は、第2引数に「 JSON_UNESCAPED_UNICODE 」と言う定数Flagを設定します。

JSON_UNESCAPED_UNICODEを設定すると、マルチバイト文字をそのままの形式で扱ってくれるので、他のプログラムに対して、日本語のままデータの受け渡しができます。

<?php

// [ 日本語をjson_encodeする ] 

$robotama_price = [
    'ロボ玉試作1号機' => '1000円',
    'ロボ玉試作2号機' => '2000円',
    'ロボ玉試作3号機' => '3000円'
];


// 日本語を含む配列をJSON形式に変換
$price_json = json_encode($robotama_price);

// すると、UniCodeエスケープされている、、、
echo $price_json;
echo "\n";
// {
//    "\u30ed\u30dc\u7389\u8a66\u4f5c1\u53f7\u6a5f":"1000\u5186",
//    "\u30ed\u30dc\u7389\u8a66\u4f5c2\u53f7\u6a5f":"2000\u5186",
//    "\u30ed\u30dc\u7389\u8a66\u4f5c3\u53f7\u6a5f":"3000\u5186"
// }


// 日本語をそのまま表示したい時は、、、
// 定数Flag「JSON_UNESCAPED_UNICODE」を第2引数に設定する!
$price_json_japan= json_encode($robotama_price, JSON_UNESCAPED_UNICODE);
echo $price_json_japan;
echo "\n";
// {"ロボ玉試作1号機":"1000円","ロボ玉試作2号機":"2000円","ロボ玉試作3号機":"3000円"}

Objectをjson_encodeする時の注意点

PHPのObjectを json_encode() でJSONデータにする時に注意したいのは、次の3点です。

  1. publicのデータはJSONデータには変換されずスルー(無視)される。
  2. function(メソッド)はJSONデータには変換されずスルー(無視)される。
  3. 元がObjectだからなのか、Objectが文字列化される。
<?php

class Robotama {
    public $name = 'ロボ玉';
    public $robotama_flag = true;

    private $like = 'ひまわりの種';

    public function hello() {
        echo 'ロボ玉なのだ!';
    }
}

// Instance(Object)
$robotamaInstance = new Robotama;


$robotama_json = json_encode($robotamaInstance, JSON_UNESCAPED_UNICODE);

// publicのデータやfunctionのデータは、JSONデータには変換されずスルーされる!
var_export($robotama_json);
echo "\n";
// '{"name":"ロボ玉","robotama_flag":true}'

JSONデータをPHPのデータに変換する json_decodeの使い方

JSONデータをPHPのデータに変換する時は、json_decode() を使います。

PHP-Manualの説明は、次のとおりです。

json_decode() は、JSON形式にエンコードされた文字列を受け取って、PHPのデータに変換(decode)します。

jsonデータを解析して、元のデータ構造に近い形に戻す。

json_decode — JSON 文字列をデコードする

[ 説明 ]

json_decode(

    string $json,

    ?bool $associative = null,

    int $depth = 512,

    int $flags = 0

): mixed

JSON エンコードされた文字列を受け取り、それを PHP の変数に変換します。

[ パラメータ ]

1. json : デコード対象となる json 文字列。

この関数は UTF-8 でエンコードされた文字列でのみ動作します。

2. associative : true の場合、返されるオブジェクトは連想配列形式になります。 

false の場合、返されるオブジェクトは object になります。 

null の場合、返されるオブジェクトは flags に 

JSON_OBJECT_AS_ARRAY が設定されているかどうかによって、

連想配列形式か object かが変化します。

3. depth : デコードするデータのネストの深さの最大値。

この値は 0 より大きく、 2147483647 以下でなければいけません。

4. flags : JSON_OBJECT_AS_ARRAYなどの定数のFlagです。

[ 戻り値 ]

json でエンコードされたデータを、適切な PHP の型として返します。 

truefalse および null はそれぞれ truefalse そして null として返されます。 

json のデコードに失敗したり エンコードされたデータがネストの最大値を超えているなどの場合、null を返します。

引用元 : PHP-Manual: json_decode
<?php

$gunma_teikoku = ['kiryu', 'maebashi', 'takasaki'];

// JSON形式に変換
$gunma_json = json_encode($gunma_teikoku);


// 1. 通常の配列は「associativeフラグ」が「true」でも「false」でも構造は変わらない!
$gunma_decode = json_decode($gunma_json, false);

var_export($gunma_decode);
echo "\n";
// array (
//     0 => 'kiryu',
//     1 => 'maebashi',
//     2 => 'takasaki',
// )

// 2. 通常の配列は「associativeフラグ」が「true」でも「false」でも構造は変わらない!
$gunma_decode_associative = json_decode($gunma_json, true);

var_export($gunma_decode_associative);
echo "\n";
// array (
//     0 => 'kiryu',
//     1 => 'maebashi',
//     2 => 'takasaki',
//   )

連想配列やObjectの json_decode() は associativeフラグを活用する

json_decode()をする際に注意したいのは、連想配列やObjectに対したは associativeフラグを活用すべき点です。

associative(連想)フラグは、json_decode() の第2引数に設定する真偽値で trueなら「連想配列」, falseなら「Object」の形のままDecodeします。

json_encode() する際に、連想配列はObjectの構造に変換されるので、

逆に考えれば、JSONデータをPHPのデータにする時は「連想配列」にdecodeするか「Object」にdecodeするか選べると言うことなのでしょう。

<?php

// 1. 「associative」フラグ が関係してくるのは、連想配列 や Object

// associative(連想)フラグが「false」 => Objectの形のままDecode

// associative(連想)フラグが「true」 => 連想配列の形でDecode

// 2. 連想配列
$robotama_price = [
    'ロボ玉試作1号機' => '1000円',
    'ロボ玉試作2号機' => '2000円',
    'ロボ玉試作3号機' => '3000円'
];


// JSON形式に変換
$price_json = json_encode($robotama_price);

// 3. json_decode(連想配列) Ver. associative_flag: false
$price_decode = json_decode($price_json, false);

// associative(連想)フラグが「false」 => Objectの形のままDecode
var_export($price_decode);
echo "\n";
// (object) array(
//     'ロボ玉試作1号機' => '1000円',
//     'ロボ玉試作2号機' => '2000円',
//     'ロボ玉試作3号機' => '3000円',
// )

// 4. json_decode(連想配列) Ver. associative_flag: true
$price_decode_associative = json_decode($price_json, true);

// associative(連想)フラグが「true」 => 連想配列の形でDecode
var_export($price_decode_associative);
echo "\n";
// array (
//     'ロボ玉試作1号機' => '1000円',
//     'ロボ玉試作2号機' => '2000円',
//     'ロボ玉試作3号機' => '3000円',
//   )


class Robotama {
    public $name = 'ロボ玉';
    public $robotama_flag = true;

    private $like = 'ひまわりの種';

    public function hello() {
        echo 'ロボ玉なのだ!';
    }
}

// 5. Instance(Object)
$robotamaInstance = new Robotama;

$robotama_json = json_encode($robotamaInstance, JSON_UNESCAPED_UNICODE);

// 6. Objectの json_decode() Ver. associative_flag: false
$robotama_decode = json_decode($robotama_json, false);

// associative(連想)フラグが「false」 => Objectの形のままDecode
var_export($robotama_decode);
echo "\n";
// (object) array(
//     'name' => 'ロボ玉',
//     'robotama_flag' => true,
//  )

// 7. Objectの json_decode() Ver. associative_flag: true
$robotama_decode_associative = json_decode($robotama_json, true);

// associative(連想)フラグが「true」 => 連想配列の形でDecode
var_export($robotama_decode_associative);
echo "\n";
// array (
//     'name' => 'ロボ玉',
//     'robotama_flag' => true,
//   )

SampleCode全文

<?php

// [ json_encode() と json_decode の使い方 ]

// JSON => JavaScript の Object の Notation(記法)

// データ形式の1つで、プログラム同士でデータをやり取りするためにある。

// ClientSide と SeverSideのデータのやり取りのため。


// [ json_encodeとは ]

// 指定した値をJSON形式に変換するには、json_encode関数を使用します。


$gunma_teikoku = ['kiryu', 'maebashi', 'takasaki'];

// JSON形式に変換
$gunma_json = json_encode($gunma_teikoku);

echo $gunma_json;
echo "\n";
// ["kiryu","maebashi","takasaki"]


// 配列を作成
$from_array = [
    'robotama' => 'gunma',
    'robotama-1'=> 'saitama',
    'robotama-2'=> 'tokyo',
    'robotama-3' => 'kanagawa',
    'neo-robotama' => 'okinawa'
];

// JSON形式に変換
$from_json = json_encode($from_array);

echo $from_json;
echo "\n";
// {"robotama":"gunma","robotama-1":"saitama","robotama-2":"tokyo","robotama-3":"kanagawa","neo-robotama":"okinawa"}



// [ 日本語をjson_encodeする ] 

    // 日本語が含まれる配列をjson_encodeでエンコードすると、日本語が文字コードで表示されてしまいます。

    // そのため、日本語をjson_encodeするには、第二引数にJSON_UNESCAPED_UNICODEを指定します。

    // JSON_UNESCAPED_UNICODEを指定すると、マルチバイト文字をそのままの形式で扱います。

$robotama_price = [
    'ロボ玉試作1号機' => '1000円',
    'ロボ玉試作2号機' => '2000円',
    'ロボ玉試作3号機' => '3000円'
];


// JSON形式に変換
$price_json = json_encode($robotama_price);

echo $price_json;
echo "\n";
// {
//    "\u30ed\u30dc\u7389\u8a66\u4f5c1\u53f7\u6a5f":"1000\u5186",
//    "\u30ed\u30dc\u7389\u8a66\u4f5c2\u53f7\u6a5f":"2000\u5186",
//    "\u30ed\u30dc\u7389\u8a66\u4f5c3\u53f7\u6a5f":"3000\u5186"
// }


// 日本語がUniCodeエスケープしないように設定する
$price_json_japan= json_encode($robotama_price, JSON_UNESCAPED_UNICODE);
echo $price_json_japan;
echo "\n";
// {"ロボ玉試作1号機":"1000円","ロボ玉試作2号機":"2000円","ロボ玉試作3号機":"3000円"}


class Robotama {
    public $name = 'ロボ玉';
    public $robotama_flag = true;

    private $like = 'ひまわりの種';

    public function hello() {
        echo 'ロボ玉なのだ!';
    }
}

// [ Instance(Object) ]
$robotamaInstance = new Robotama;


$robotama_json = json_encode($robotamaInstance, JSON_UNESCAPED_UNICODE);

var_export($robotama_json);
echo "\n";
// '{"name":"ロボ玉","robotama_flag":true}'




// [ json_decodeとは ]

// JSON形式にエンコードされた文字列を受け取って、デコードするにはjson_decode関数を使用します。

// デコードとは、簡単に説明するとエンコードされたデータを元に戻すことを言います。


// jsonデータを解析して、元のデータ構造に近い形に戻す。

// 「associative」フラグ

// true の場合、返されるオブジェクトは連想配列形式になります。 false の場合、返されるオブジェクトは object になります。 
// null の場合、返されるオブジェクトは flags に JSON_OBJECT_AS_ARRAY が設定されているかどうかによって、 連想配列形式か object かが変化します。


// 1. 通常の配列は、true でも false でも Arrayの構造は変わらない!

$gunma_decode = json_decode($gunma_json, false);

var_export($gunma_decode);
echo "\n";
// array (
//     0 => 'kiryu',
//     1 => 'maebashi',
//     2 => 'takasaki',
// )


$gunma_decode_associative = json_decode($gunma_json, true);

var_export($gunma_decode_associative);
echo "\n";
// array (
//     0 => 'kiryu',
//     1 => 'maebashi',
//     2 => 'takasaki',
//   )


// 2. 「associative」フラグ が関係してくるのは、連想配列 や Object

// associative(連想)フラグが「false」 => Objectの形のままDecode

//  associative(連想)フラグが「true」 => 連想配列の形でDecode

$from_decode = json_decode($from_json, false);

var_export($from_decode);
echo "\n";
// (object) array(
//     'robotama' => 'gunma',
//     'robotama-1' => 'saitama',
//     'robotama-2' => 'tokyo',
//     'robotama-3' => 'kanagawa',
//     'neo-robotama' => 'okinawa',
// )

$from_decode_associative = json_decode($from_json, true);


var_export($from_decode_associative);
echo "\n";
// array (
//     'robotama' => 'gunma',
//     'robotama-1' => 'saitama',
//     'robotama-2' => 'tokyo',
//     'robotama-3' => 'kanagawa',
//     'neo-robotama' => 'okinawa',
//   )


$price_decode = json_decode($price_json, false);

var_export($price_decode);
echo "\n";

// (object) array(
//     'ロボ玉試作1号機' => '1000円',
//     'ロボ玉試作2号機' => '2000円',
//     'ロボ玉試作3号機' => '3000円',
// )


$price_decode_associative = json_decode($price_json, true);

var_export($price_decode_associative);
echo "\n";
// array (
//     'ロボ玉試作1号機' => '1000円',
//     'ロボ玉試作2号機' => '2000円',
//     'ロボ玉試作3号機' => '3000円',
//   )



$robotama_decode = json_decode($robotama_json, false);

var_export($robotama_decode);
echo "\n";
// (object) array(
//     'name' => 'ロボ玉',
//     'robotama_flag' => true,
//  )


$robotama_decode_associative = json_decode($robotama_json, true);

var_export($robotama_decode_associative);
echo "\n";
// array (
//     'name' => 'ロボ玉',
//     'robotama_flag' => true,
//   )

Twitterやってます!Follow Me!

神聖グンマー帝国の逆襲🔥

神聖グンマー帝国の科学は、世界一ぃぃぃぃぃぃ!!!!!

PHP / Laravel書籍

参考・引用

  1. PHP-Manual: json_encode
  2. PHP-Manual: json_decode
  3. 【PHP入門】JSONのデータを処理する方法(json_encode/json_decode)

最近の投稿