先決條件: | 基本的計算機素養(yǎng),對HTML和CSS的基本了解,熟悉JavaScript基礎知識(請參見第一步和構(gòu)建塊 / a>)和OOJS基礎知識(請參見對象簡介)。 |
---|---|
目的: | 要了解如何使用存儲在JSON中的數(shù)據(jù),并創(chuàng)建自己的JSON對象。 |
JSON 是一種數(shù)據(jù)格式,遵循JavaScript對象語法,該語法由 a class ="external"> Douglas Crockford 。 即使它是基于JavaScript語法,它可以獨立于JavaScript使用,并且許多編程環(huán)境具有讀取(解析)和生成JSON的能力。
JSON可以作為對象或字符串存在 - 前者用于從JSON讀取數(shù)據(jù),后者用于在網(wǎng)絡上發(fā)送JSON。 這不是一個大問題 - JavaScript提供了一個全局 JSON 對象 有可用于在兩者之間轉(zhuǎn)換的方法。
JSON對象可以存儲在自己的文件中,基本上只是一個擴展名為 .json
和 mozilla.org/zh-CN/docs/Glossary/MIME_type\"> MIME類型的 application / json
。
我們在上面已經(jīng)暗示,JSON對象基本上是一個JavaScript對象,這是最正確的。 您可以在JSON中包含與標準JavaScript對象(字符串,數(shù)字,數(shù)組,布爾值和其他對象字面值)中相同的基本數(shù)據(jù)類型。 這允許您構(gòu)造數(shù)據(jù)層次結(jié)構(gòu),如下所示:
{ ? "squadName" : "Super hero squad", ? "homeTown" : "Metro City", ? "formed" : 2016, ? "secretBase" : "Super tower", "active" : true, ? "members" : [ ??? { ????? "name" : "Molecule Man", ????? "age" : 29, ????? "secretIdentity" : "Dan Jukes", ????? "powers" : [ ??????? "Radiation resistance", ??????? "Turning tiny", ??????? "Radiation blast" ????? ] ??? }, ??? { ????? "name" : "Madame Uppercut", ????? "age" : 39, ????? "secretIdentity" : "Jane Wilson", ????? "powers" : [ ??????? "Million tonne punch", ??????? "Damage resistance", ??????? "Superhuman reflexes" ????? ] ??? }, ??? { ????? "name" : "Eternal Flame", ????? "age" : 1000000, ????? "secretIdentity" : "Unknown", ????? "powers" : [ ??????? "Immortality", ??????? "Heat Immunity", ??????? "Inferno", ??????? "Teleportation", ??????? "Interdimensional travel" ????? ] ??? } ? ] }
如果我們將這個對象加載到JavaScript程序中,保存在一個叫做 superHeroes
的變量中,我們就可以使用我們在 "/ webstart / Objects / Basics"> JavaScript對象基礎文章。 例如:
superHeroes.hometown superHeroes["active"]
要在層次結(jié)構(gòu)中進一步訪問數(shù)據(jù),您只需將所需的屬性名稱和數(shù)組索引鏈接在一起。 例如,要訪問成員列表中列出的第二個英雄的第三超級大國,您可以這樣做:
superHeroes["members"][1]["powers"][2]
superHeroes
.members
property, so we use ["members"]
.members
contains an array populated by objects. We want to access the second object inside the array, so we use [1]
.powers
property, so we use ["powers"]
.powers
property is an array containing the selected hero's superpowers. We want the third one, so we use [2]
.注意:我們已在上面的 /json/JSONTest.html\">JSONText.html 示例(請參閱 /json/JSONTest.html\">源代碼)。 嘗試加載,然后通過瀏覽器的JavaScript控制臺訪問變量中的數(shù)據(jù)。
上面我們說"我們已經(jīng)暗示JSON對象基本上是一個JavaScript對象,這是正確的" - 我們說"大多數(shù)正確"的原因是因為數(shù)組也可以是一個有效的JSON對象,例如:
[ { "name" : "Molecule Man", "age" : 29, "secretIdentity" : "Dan Jukes", "powers" : [ "Radiation resistance", "Turning tiny", "Radiation blast" ] }, { ??? "name" : "Madame Uppercut", ??? "age" : 39, ??? "secretIdentity" : "Jane Wilson", ??? "powers" : [ ????? "Million tonne punch", ????? "Damage resistance", ????? "Superhuman reflexes" ??? ] ? } ]
上面是完全有效的JSON。 你只需要從數(shù)組索引開始訪問數(shù)組項,例如 [0] ["powers"] [0]
。
因此,讓我們通過一個例子來說明如何在網(wǎng)站上使用一些JSON數(shù)據(jù)。
首先,制作我們的英雄的本地副本。 html 和 style.css a>文件。 后者包含一些簡單的CSS來為我們的頁面設計樣式,而前者包含一些非常簡單的body HTML:
<header> </header> <section> </section>
加上 < script>
元素,以包含我們將在此處撰寫的JavaScript代碼 行使。 目前它只包含兩行,它們引用了 < header>
和 < section>
元素并將其存儲在變量中:
var header = document.querySelector('header'); var section = document.querySelector('section');
我們已將我們的JSON數(shù)據(jù)提供給我們的GitHub,網(wǎng)址為: https:/ /mdn.github.io/learning-area/javascript/oojs/json/superheroes.json 。
我們將把它加載到我們的頁面,并使用一些漂亮的DOM操作來顯示它,像這樣:
要將我們的JSON加載到我們的網(wǎng)頁中,我們將使用名為 XMLHttpRequest
的API(通常稱為 XHR )。 這是一個非常有用的JavaScript對象,它允許我們通過JavaScript(例如圖像,文本,JSON,甚至HTML片段)來從服務器檢索資源,這意味著我們可以更新內(nèi)容的小部分,而不必重新加載整個 頁。 這導致更響應的網(wǎng)頁,并聽起來令人興奮,但不幸的是超出了本文的范圍,教更多的細節(jié)。
var requestURL = 'https://mdn.github.io/learning-area/javascript/oojs/json/superheroes.json';
XMLHttpRequest
constructor, using the new
keyword. Add the following below your last line: var request = new XMLHttpRequest();
open()
method. Add the following line: request.open('GET', requestURL);
這至少需要兩個參數(shù) - 還有其他可選參數(shù)可用。 對于這個簡單的例子,我們只需要兩個強制的:
GET
is fine, as we are just retrieving some simple data.responseType
to JSON, so the server will know we want a JSON object returned, and sending the request with the send()
method: request.responseType = 'json'; request.send();
request.onload = function() { var superHeroes = request.response; populateHeader(superHeroes); showHeroes(superHeroes); }
這里我們存儲對我們的請求的響應(可在 響應
> 屬性)在一個名為 superHeroes
的變量中; 這個變量現(xiàn)在將包含我們的JSON! 然后,我們將該JSON傳遞給兩個函數(shù)調(diào)用 - 第一個將用正確的數(shù)據(jù)填充< header>
,而第二個將為團隊中的每個英雄創(chuàng)建一個信息卡, 將其插入到< section>
中。
我們將代碼包裝在事件處理程序中,當load事件觸發(fā)請求對象時運行(參見 XMLHttpRequestEventTarget / onload"> onload
) - 這是因為load事件在響應成功返回時觸發(fā); 這樣做保證 request.response
一定會可用,當我們試圖做一些事情。
現(xiàn)在我們已經(jīng)檢索了我們的JSON數(shù)據(jù),讓我們通過寫我們上面提到的兩個函數(shù)來使用它。 首先,在上面的代碼下面添加以下函數(shù)定義:
function populateHeader(jsonObj) { var myH1 = document.createElement('h1'); myH1.textContent = jsonObj['squadName']; header.appendChild(myH1); var myPara = document.createElement('p'); myPara.textContent = 'Hometown: ' + jsonObj['homeTown'] + ' // Formed: ' + jsonObj['formed']; header.appendChild(myPara); }
我們調(diào)用了參數(shù) jsonObj
,這就是我們需要調(diào)用它里面的JSON對象。 在這里,我們首先使用創(chuàng)建
> createElement() ,將其< h1>
元素 > textContent
等于 squadName
屬性 JSON,然后使用 appendChild()將其附加到標題
。 然后,我們對一個段落進行非常類似的操作:創(chuàng)建它,設置其文本內(nèi)容并將其附加到標題。 唯一的區(qū)別是其文本設置為包含JSON的 homeTown
和形成
屬性的連接字符串。
接下來,在代碼的底部添加以下函數(shù),創(chuàng)建并顯示超級英雄卡:
function showHeroes(jsonObj) { var heroes = jsonObj['members']; for(i = 0; i < heroes.length; i++) { var myArticle = document.createElement('article'); var myH2 = document.createElement('h2'); var myPara1 = document.createElement('p'); var myPara2 = document.createElement('p'); var myPara3 = document.createElement('p'); var myList = document.createElement('ul'); myH2.textContent = heroes[i].name; myPara1.textContent = 'Secret identity: ' + heroes[i].secretIdentity; myPara2.textContent = 'Age: ' + heroes[i].age; myPara3.textContent = 'Superpowers:'; var superPowers = heroes[i].powers; for(j = 0; j < superPowers.length; j++) { var listItem = document.createElement('li'); listItem.textContent = superPowers[j]; myList.appendChild(listItem); } myArticle.appendChild(myH2); myArticle.appendChild(myPara1); myArticle.appendChild(myPara2); myArticle.appendChild(myPara3); myArticle.appendChild(myList); section.appendChild(myArticle); } }
首先,我們將JSON的 members
屬性存儲在一個新變量中。 此數(shù)組包含多個對象,其中包含每個英雄的信息。
接下來,我們使用 for循環(huán)循環(huán)訪問數(shù)組中的每個對象。 對于每一個,我們:
<article>
, an <h2>
, three <p>
s, and a <ul>
.name
.secretIdentity
, age
, and a line saying "Superpowers:" to introduce the information in the list.powers
property in another new variable called superPowers
— this contains an array that lists the current hero's superpowers.for
loop to loop through the current hero's superpowers — for each one we create a <li>
element, put the superpower inside it, then put the listItem
inside the <ul>
element (myList
) using appendChild()
.<h2>
, <p>
s, and <ul>
inside the <article>
(myArticle
), then append the <article>
inside the <section>
. The order in which things are appended is important, as this is the order they will be displayed inside the HTML.注意:如果您無法使示例工作,請嘗試參考我們的 master / javascript / oojs / json / heroes-finished.html"> heroes-finished.html 源代碼(參見 -area / javascript / oojs / json / heroes-finished.html">運行實時)。
注意:如果您在使用我們用于訪問JSON的點/括號符號時遇到問題,可以使用 github.io/learning-area/javascript/oojs/json/superheroes.json\">superheroes.json 文件在另一個選項卡或文本編輯器中打開,并在查看我們的JavaScript時參考它。 您還應參閱我們的 JavaScript對象基礎知識文章,了解點和括號符號的更多信息。
上面的例子在訪問JSON方面很簡單,因為我們設置XHR以JSON格式返回響應,使用:
request.responseType = 'json';
但有時我們不那么幸運 - 有時我們會收到一些格式化為文本字符串的JSON數(shù)據(jù),我們需要將它轉(zhuǎn)換為一個對象。 當我們想要發(fā)送JSON數(shù)據(jù)作為某種消息時,我們經(jīng)常需要將其轉(zhuǎn)換為字符串,以使其正常工作。 幸運的是,這兩個問題在Web開發(fā)中非常常見,內(nèi)置的 JSON / a>對象被添加到瀏覽器很久以前,包含以下兩種方法:
parse()
: Accepts a JSON object in text string form as a parameter, and returns the corresponding object.stringify()
: Accepts a JSON object as a parameter, and returns the equivalent text string form.您可以在我們的 > heroes-finished-json-parse.html example(see the json / heroes-finished-json-parse.html">源代碼) - 這與我們之前構(gòu)建的示例完全相同,只是我們設置XHR將JSON作為文本返回,然后使用 parse()
將其轉(zhuǎn)換為實際的JSON對象。 代碼的關鍵代碼片段在這里:
request.open('GET', requestURL); request.responseType = 'text'; // now we're getting a string! request.send(); request.onload = function() { var superHeroesText = request.response; // get the string from the response var superHeroes = JSON.parse(superHeroesText); // convert it to an object populateHeader(superHeroes); showHeroes(superHeroes); }
正如你可能猜到的, stringify()
工作方式相反。 嘗試在瀏覽器的JavaScript控制臺中輸入以下行,以便在操作中查看它:
var myJSON = { "name" : "Chris", "age" : "38" }; myJSON var myString = JSON.stringify(myJSON); myString
這里我們創(chuàng)建一個JSON對象,然后檢查它包含什么,然后使用 stringify()
將返回值保存在一個新的變量,然后再次檢查它轉(zhuǎn)換為字符串。
在本文中,我們?yōu)槟峁┝嗽诔绦蛑惺褂肑SON的簡單指南,包括如何創(chuàng)建和解析JSON,以及如何訪問其中鎖定的數(shù)據(jù)。 在下一篇文章中,我們將開始討論面向?qū)ο蟮腏avaScript。
更多建議: