2017-03-22 76 views
0

我目前正在研究一些Python代碼以獲取JSON文件的某些文本元素,並將此文本以'spell name': 'description'格式寫入文件。例如,採取以下JSON文件的名稱和簡短說明元素(編輯爲簡潔起見):正在寫入文本文件

[ 
    { 
     "pk": 0, 
     "model": "srd20.spell", 
     "fields": { 
      "description": "<p>An arrow of acid springs from your hand and speeds to its target. You must succeed on a <a href=\"../combat.html#_ranged-touch-spells-in-combat-95\">ranged touch attack</a> to hit your target. The arrow deals 2d4 points of acid damage with no splash damage. For every three caster levels you possess, the acid, unless neutralized, lasts for another round (to a maximum of 6 additional rounds at 18th level), dealing another 2d4 points of damage in each round.</p>", 
      "school": "conjuration", 
      "saving_throw": "none", 
      "name": "Acid Arrow", 
      "reference": "prd/spells", 
      "level": "sorcerer/wizard 2", 
      "spell_resistance": "no", 
      "area": "", 
      "casting_time": "1 standard action", 
      "effect": "one arrow of acid", 
      "descriptor": "acid", 
      "range": "long (400 ft. + 40 ft./level)", 
      "short_description": "Ranged touch attack; 2d4 damage for 1 round + 1 round/3 levels.", 
      "components": "V, S, M (rhubarb leaf and an adder's stomach), F (a dart)", 
      "altname": "acid-arrow", 
      "duration": "1 round + 1 round per three levels", 
      "subschool": "creation", 
      "target": "" 
     } 
    }, 
... 
] 

,寫這些細節到一個文件中,像這樣:

'Acid Arrow': 'Ranged touch attack; 2d4 damage for 1 round + 1 round/3 levels.', 

我至今似乎幾乎做的伎倆。它採用JSON,貫穿每一個元素(名單上的拼寫)和格式寫入該咒語的名稱和描述,該文件spelllistparsed.txt我想:

import json 

fWrite = open('spelllistparsed.txt', 'w') 

with open('spells.json') as data_file: 
    data = json.load(data_file) 

for count, item in enumerate(data, start=0): 
    fWrite.write("'" + data[count]["fields"]["name"] + "': " + "'" 
       + data[count]["fields"]["short_description"] + "',\n") 

但問題是,當我運行該程序時,它只會將部分列表寫入新文件。當我運行它時,最終的結果將顯示在應該存在的千位左右中的大約30個法術。基於一些試驗和錯誤,我發現了以下幾件事:

  • 無論使用哪種方法進行迭代,這似乎都會發生。我已經嘗試使用整數計數,而且它們的結果是相同的。也嘗試增加2 - 所有其他法術都會被寫入,但在大約50個左右的法術後它仍然會被切斷。
  • 當我爲法術使用不同的第二個領域(不是「short_description」,而是咒語的不同元素,如「描述」或「效果」)時,將不同數量的文本寫入文件。對於短文本,將顯示所有1000個左右的文字spell name : second field,對於第二個字段中的大量文本,它只會向spelllistparsed.txt寫入一些法術。我不認爲寫入文件的內容有特定的字符限制,但這看起來似乎是問題的一部分
  • 當我將第二個字段設置爲始終打印相同的東西(data[0]["fields"]["short_description"])時,它成功寫的所有法術的文件作爲'spell name': 'description for spell 0',所以這個問題可能是處理許多不同的描述
  • 據我所知道的JSON是有效的,這應該是可能的(運行它通過JSONLint)
  • 當運行當前的代碼它寫入文件的法術酸箭通過Baleful Polymorph

任何幫助woul d非常感謝!我覺得這應該是相對簡單的,但這是我第一次使用Python,並且我的搜索解決方案迄今爲止沒有結果。讓我知道是否有任何其他信息我應該包括在這裏,可以幫助。法術

JSON文件:https://github.com/machinalis/django-srd20/blob/master/pathfinder/spells.json

回答

0

Python2負載JSON字符串作爲unicode對象,這就需要進行編碼纔可以寫入到一個文件對象。第31項中腳本失敗的原因是因爲這顯然是第一個包含非ASCII字符的項目(在本例中爲U + 2013「 - 」)。

你會想你的代碼看起來像這樣:

import json 

fWrite = open('spelllistparsed.txt', 'w') 

with open('spells.json') as data_file: 
    data = json.load(data_file) 

# note that you do not need to use enumerate here as you never use the index 
for item in data: 
    name = item["fields"]["name"].encode("utf-8") 
    desc = item["fields"]["short_description"].encode("utf-8") 
    fWrite.write("'" + name + "': " + "'" + desc + "',\n") 

# always close open files when you're done! 
fWrite.close() 

或者,你可以使用Python3,在這種情況下,你只需要關鍵字參數encoding='utf-8'添加到第一次調用open在你的腳本中。而且你還想在最後關閉文件。

+0

謝謝你的幫助和解釋 - 這解決了我的問題! – dacharya64

0

您需要在文件的末尾做fWrite.close()或者使用與法術文件相同的「with」上下文管理器。

Python存在時文件關閉,但文件輸出通常被緩衝,如果沒有換行符,則掛起的輸出不會刷新到文件系統。

0

可以使用Python2其獲取從給定的URL數據嘗試這個例子:使用

from urllib.request import urlopen 
from json import loads 
# Fetching the data from this URL 
url = "https://raw.githubusercontent.com/machinalis/django-srd20/master/pathfinder/spells.json" 

def load_from_url(url = ""): 
    with urlopen(url) as data: 
     response = data.read() 
     return loads(response.decode('utf-8')) 


def get_data(data = ""): 
    # New file is called new_data 
    with open("new_data", "a") as f: 
     for k in data: 
      f.write("'{0}':'{1}',\n".format(k["fields"]["name"], k["fields"]["short_description"])) 

data = load_from_url(url) 
get_data(data) 

輸出(用於代碼:

from urllib2 import urlopen 
from json import loads 
# Fetching the data from this URL 
url = "https://raw.githubusercontent.com/machinalis/django-srd20/master/pathfinder/spells.json" 

def load_from_url(url = ""): 
    data = urlopen(url) 
    response = data.read() 
    return loads(response.decode('utf-8')) 


def get_data(data = ""): 
    # The output file is called new_data 
    with open("new_data", "a") as f: 
     for k in data: 
      f.write("'%s':'%s',\n" % (k["fields"]["name"].encode('utf-8'), k["fields"]["short_description"].encode('utf-8'))) 

data = load_from_url(url) 
get_data(data) 

此外,您還可以在Python3實現任務Python2 and Python3

'Acid Arrow':'Ranged touch attack; 2d4 damage for 1 round + 1 round/3 levels.', 
'Acid Fog':'Fog deals acid damage.', 
'Acid Splash':'Orb deals 1d3 acid damage.', 
'Aid':'+1 on attack rolls and saves against fear, 1d8 temporary hp +1/level (max +10).', 
'Air Walk':'Subject treads on air as if solid (climb or descend at 45-degree angle).', 
'Alarm':'Wards an area for 2 hours/level.', 
'Align Weapon':'Weapon becomes good, evil, lawful, or chaotic.', 

... 

'Weaken Powder':'Targeted firearm's ammunition halves the firearm's range and imposes a –2 penalty on damage rolls.', 
'Wilderness Soldiers':'Nearby plants aid you in combat.', 
'Wreath of Blades':'Four mithral daggers speed around you, attacking nearby creatures and protecting your spellcasting from attacks of opportunity.',