質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

87.79%

JSON.parseが効かない

解決済

回答 4

投稿

  • 評価
  • クリップ 0
  • VIEW 985

score 1

前提

PHPの配列をコメントアウト付きで出力したいので、hoge(); を実行してヒアドキュメントで出力しています。

実現したいこと

こうして出力されたものをJSON.parseして、JSで配列として扱いたいです。

発生している問題・エラーメッセージ

JSON.parseができません。

該当のソースコード

PHPファイルから以下の配列を、コメントアウト付きで出力しています。

hoge();
function hoge(){    
    $str = <<<EOM
    [
        [
        /*
            コメント
        */
            /*
             コメント
            ---------------------------*/
            // コメント
            'key1'=>1,
            // コメント
            'key2'=>2,

            /*
             コメント
            ---------------------------*/    
            // コメント
            'key3'=>3
        ],    
    ];
EOM;
    echo $str;
}


上記PHPを出力するHTMLは以下です。

<pre><?php print_r( hoge() ); ?></pre>

試したこと

上記$str ( preの中のテキスト ) をJSON.parseするために、変更箇所は以下3つだと考えています。

「=>」を「:」に変える
「// コメント」を削除
「/* コメント */」を削除

この3つを実行したのが以下コードです。

    // preの中のテキスト
    var str = $('pre').text();

    // 「=>」を「:」に変える
    var tmp1 = str.replace(/^=>$/, ':');

    // 「// コメント」を削除
    var tmp2 = tmp1.replace(/^\/\/\s.+\n$/, '');

    // 「/* コメント */」を削除
    var result = tmp2.replace(/^\/\*\n.+\n\*\/$/, '');

    // 結果
    console.log(result);


ですが、JSON.parseが効かないようで、$strを配列にすることができません。
このようなときの解決策をご指南頂きたく存じます。
宜しくお願い申し上げます。

補足情報

尚、$strをJSで配列として扱いたいというのは、$strを以下resultにしてJSで扱いたいという意味です。
これを目指しているのが上記試したことにある3つの処理になります。

    var result = [
        {
            'key1': 1,
            'key2': 2,
            'key3': 3
        },    
    ];
  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • m.ts10806

    2020/05/10 13:27

    いえ、違います。PHP側で正しいJSON文字列を作ればわざわざJavaScriptで組む必要はありません。
    そもそもJSONでは基本的にコメントが使えないわけですが、コメント説明が必要なキーや値などの情報を持たせるというのはデータの持ち方としてはNGです。
    どうしても書きたいならJSON外の外でPHPのコメントを書きましょう。
    置換が沢山必要なプログラム自体、かなり問題があります。イレギュラーに対応しきれません。

    キャンセル

  • inoki

    2020/05/10 13:38

    >コメント説明が必要なキーや値などの情報を持たせるというのはデータの持ち方としてはNGです。
    >置換が沢山必要なプログラム自体、かなり問題があります。イレギュラーに対応しきれません。
    いやそういう決まりなんです。テスト用サイトなので、あまり気にしないでください。

    キャンセル

  • m.ts10806

    2020/05/10 13:40

    なるほどそれなら仕方ないと言えば仕方ないですが、パターンケースが不明なのであえてやろうとは思わないですね。
    それにしても、HTMLに表示させてからJavaScriptでなんとかするより、PHPで加工すべきというところは動きませんけど。

    キャンセル

回答 4

checkベストアンサー

+3

JSON

JSONにコメントはありません。
JSON構文に違反しない範囲で、コメントを埋め込むなら、プロパティに埋め込む事になるでしょう。

var array = [
  {descrypter: {key1: 'key1の説明', key2: 'key2の説明', key3: 'key3の説明'}},
  {key1: 1, key2: 2, key3: 3},
  {key1: 1, key2: 2, key3: 3},
  {key1: 1, key2: 2, key3: 3}
];

console.log(JSON.stringify(array)); // [{"descrypter":{"key1":"key1の説明","key2":"key2の説明","key3":"key3の説明"}},{"key1":1,"key2":2,"key3":3},{"key1":1,"key2":2,"key3":3},{"key1":1,"key2":2,"key3":3}]

json_encode()

JSONを出力する為に文字列を手動出力するのは筋が悪く、定義済のエンコード関数を使うべきかと思います。

YAML

どうしても、コメントでなければならないのなら、コメントが定義されているYAMLなど、別のフォーマットを採用します。

Re: inoki さん

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2020/05/11 00:29

    ご丁寧にどうもありがとうございます。助かりました。

    キャンセル

+2

とりあえずjsonらしくするなら、キーをエンクローズするのは
ダブルクォートにして、配列の最後の要素の後ろにはカンマを入れないでください

ちゃんとやるなら変換するのではなく、コメント有り無しふたつ
用意することです、今のままだと効率化されずにかえって負担が増えてるだけです

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2020/05/10 15:18

    たしかに有り無しふたつ用意すれば解決するのですが、やはり同じものを書くところに抵抗を感じます。しかしその抵抗感よりも、変換の不便さを悪く見積もるべきでしょうか。

    キャンセル

  • 2020/05/10 15:44

    とりあえずその前に指摘した方法を試してください

    キャンセル

  • 2020/05/10 22:45 編集

    指摘した方法というのは、ダブルクオートとカンマですか?たしかに仰る通りその方がjsonらしいのでそうすべきですね。

    キャンセル

+2

とりあえず気になる部分だけ。

        ],    
    ];

JSON形式としては次に要素がない,はNGですし(JavaScriptオブジェクトには変換できる)、特に最後の;はあってはいけませんね。PHPのjson_decode()も通らないです。

<?php
$jsonstr = <<<E
[[],]
E;
var_dump(json_decode($jsonstr));
//NULL

$jsonstr = <<<E
[[]]
E;
var_dump(json_decode($jsonstr));
/**
array(1) {
  [0]=>
  array(0) {
  }
}
**/


$jsonstr = <<<E
[];
E;
var_dump(json_decode($jsonstr));
// NULL

$jsonstr = <<<E
[]
E;
var_dump(json_decode($jsonstr));
/**
array(0) {
}
**/

「何を消すか」ではなく「正しいJSON文字列を構築する」ことを主眼にしてください。
※だから本来蛇足である部分をわざわざ付け足して消すというのは悪手でしかないという指摘なんですが

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2020/05/10 22:49

    PHPの配列をコメントアウト付きで出力したいというのが前提なのでそこは守りたいです。

    キャンセル

  • 2020/05/11 06:21 編集

    どの回答も、「前提がおかしいので構造・設計から見直すべき」と言う意見しかないですね。私ならその前提がなぜ必要なのかをしっかりと議論します。
    inokiさんから出てくるコメントには納得できる理由が一切ありません。

    キャンセル

  • 2020/05/11 08:15

    一応、YAMLを使えば、期待通りの動作にはなりますね。

    最も、質問の閉じ方に疑問は感じます。 >BAのどの手順を使って解決したのかを書いていない
    https://teratail.com/help/question-tips#questionTips4-2

    キャンセル

  • 2020/05/11 09:06

    >最も、質問の閉じ方に疑問は感じます
    同じく。フィードバックは何かしら欲しいですね。
    「ありがとう」より「こういう風に理解した」「こうやって解決した」というコメントの方が嬉しいものなんですが。

    キャンセル

+1

PHPファイルから以下の配列を、コメントアウト付きで出力

以下の配列 という解釈は正しいのでしょうか。

ヒアドキュメントは文字列であって、配列ではないはずです。
print_r() をみると、php のソースコードとして書かれた配列であるなら納得できるのですが、文字列の場合は引数に渡す前に、eval()などで配列に展開する必要があるのではないでしょうか。

JSON.parseして、JSで配列として扱いたい

JSON.parse() したいのであれば 仕様として採用されているjson.org のノーテーションを守る必要があります。
PHPのコメント文は解釈できませんので、切り捨てるか comment など任意のキー(JSONのプロパティ)を追加するなどしてデータ構造を改変する必要があります。

扱いたい のであれば、マニュアルや仕様を精査して、扱えるかどうかを調べてください。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2020/05/11 00:30

    PHPにあるコメントをHTMLに表示したいので、ヒアドキュメントをと考えた感じでした。アドバイスありがとうございました。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 87.79%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る