如何将JSON数据写入文件?

use*_*318 992 python json

我将JSON数据存储在变量中data.

我想将其写入文本文件进行测试,因此我不必每次都从服务器获取数据.

目前,我正在尝试这个:

obj = open('data.txt', 'wb')
obj.write(data)
obj.close
Run Code Online (Sandbox Code Playgroud)

我收到错误:

TypeError: must be string or buffer, not dict

如何解决这个问题?

phi*_*hag 1831

你忘了实际的JSON部分 - data是一个字典,还没有JSON编码.写这样:

import json
with open('data.json', 'w') as f:
    json.dump(data, f)
Run Code Online (Sandbox Code Playgroud)

注意:适用于3.x和2.x.

  • @TerminalDilettante`json.dump`写入文件或类文件对象,而`json.dumps`返回一个字符串. (137认同)
  • btw:重新读取数据使用:使用open('data.txt')作为infile:d = json.load(infile).请参阅:[此答案](http://stackoverflow.com/questions/20199126/reading-a-json-file-using-python) (24认同)
  • 你的意思是json.dump还是json.dumps? (9认同)
  • @denvar不,这个答案很精细.在Python 3上,`json.dump`写入文本文件,而不是二进制文件.如果用`wb`打开文件,你会得到一个'TypeError`.在较旧的Python版本中,`w`和`wb`都可以工作.由于`json.dump`的输出默认为ASCII,因此不需要显式编码.如果您可以确定您的代码永远不会在遗留Python版本上运行,并且您和JSON文件的处理程序可以正确处理非ASCII数据,您可以指定一个并设置`ensure_ascii = False`. (9认同)
  • 这可能有助于序列化:http://stackoverflow.com/questions/4512982/python-typeerror-cant-write-str-to-text-stream (6认同)

Ant*_*ins 255

要获得utf8编码的文件,而不是在Python 2的接受答案中使用ascii -encoded:

import io, json
with io.open('data.txt', 'w', encoding='utf-8') as f:
  f.write(json.dumps(data, ensure_ascii=False))
Run Code Online (Sandbox Code Playgroud)

Python 3中的代码更简单:

import json
with open('data.txt', 'w') as f:
  json.dump(data, f, ensure_ascii=False)
Run Code Online (Sandbox Code Playgroud)

在Windows上,encoding='utf-8'参数open仍然是必要的.

为避免将数据的编码副本存储在内存中(结果dumps)并在Python 2和3中输出utf8编码的字节串,请使用:

import json, codecs
with open('data.txt', 'wb') as f:
    json.dump(data, codecs.getwriter('utf-8')(f), ensure_ascii=False)
Run Code Online (Sandbox Code Playgroud)

codecs.getwriterPython 3中的调用是多余的,但Python 2则需要


可读性和大小:

使用ensure_ascii=False提供更好的可读性和更小的尺寸:

>>> json.dumps({'price': '€10'})
'{"price": "\\u20ac10"}'
>>> json.dumps({'price': '€10'}, ensure_ascii=False)
'{"price": "€10"}'

>>> len(json.dumps({'?????': 1}))
37
>>> len(json.dumps({'?????': 1}, ensure_ascii=False).encode('utf8'))
17
Run Code Online (Sandbox Code Playgroud)

通过向或者的参数添加标志indent=4, sort_keys=True(由dinos66建议)进一步提高可读性.这样你就可以在json文件中获得一个很好的缩进排序结构,但代价是文件大小稍大.dumpdumps

  • `unicode`是多余的 - `json.dumps`的结果已经是unicode对象了.请注意,这在3.x中失败,其中清除了整个输出文件模式,j​​son总是使用字符串(和字符I/O)而不是字节. (5认同)
  • 在2.x`type(json.dumps('a'))中``是`<type'str'>`.甚至`type(json.dumps('a',encoding ='utf8'))``是`<type'str'>`. (4认同)
  • 是的,在3.x中json使用字符串,但默认编码是ascii.你必须明确告诉它你甚至在3.x中也想要'utf8`.更新了答案. (4认同)
  • 哦,你完全正确 - 我一定很困惑.+1的详细信息. (4认同)

amb*_*odi 157

我会用前面提到的答案稍作修改来回答,那就是编写一个美化的JSON文件,人眼可以更好地阅读.为此,传递sort_keysas Trueindent4个空格字符,你很高兴.还要注意确保不会在您的JSON文件中写入ascii代码:

with open('data.txt', 'w') as outfile:
     json.dump(jsonData, outfile, sort_keys = True, indent = 4,
               ensure_ascii = False)
Run Code Online (Sandbox Code Playgroud)

  • 仍然得到`UnicodeEncodeError:'ascii'编解码器不能编码字符u'\ xfc'` (2认同)
  • +1表示sort_keys和缩进。@aesede添加此行是不好的,因为它会使该解决方案也适用于python2,但不适用于python2(带有非ascii数据的UnicodeEncodeError)。有关详细信息,请参见[我的解决方案](http://stackoverflow.com/a/14870531/237105)。 (2认同)

Mar*_*oma 106

使用Python 2 + 3读写JSON文件; 适用于unicode

# -*- coding: utf-8 -*-
import json

# Make it work for Python 2+3 and with Unicode
import io
try:
    to_unicode = unicode
except NameError:
    to_unicode = str

# Define data
data = {'a list': [1, 42, 3.141, 1337, 'help', u'€'],
        'a string': 'bla',
        'another dict': {'foo': 'bar',
                         'key': 'value',
                         'the answer': 42}}

# Write JSON file
with io.open('data.json', 'w', encoding='utf8') as outfile:
    str_ = json.dumps(data,
                      indent=4, sort_keys=True,
                      separators=(',', ': '), ensure_ascii=False)
    outfile.write(to_unicode(str_))

# Read JSON file
with open('data.json') as data_file:
    data_loaded = json.load(data_file)

print(data == data_loaded)
Run Code Online (Sandbox Code Playgroud)

参数说明json.dump:

  • indent:使用4个空格缩进每个条目,例如,当一个新的dict启动时(否则所有都将在一行中),
  • sort_keys:排序字典的键.如果要将json文件与diff工具进行比较/将它们置于版本控制之下,这非常有用.
  • separators:防止Python添加尾随空格

随着包

看看我的实用程序包mpu,以获得一个超级简单易记的实用程序:

import mpu.io
data = mpu.io.read('example.json')
mpu.io.write('example.json', data)
Run Code Online (Sandbox Code Playgroud)

创建了JSON文件

{
    "a list":[
        1,
        42,
        3.141,
        1337,
        "help",
        "€"
    ],
    "a string":"bla",
    "another dict":{
        "foo":"bar",
        "key":"value",
        "the answer":42
    }
}
Run Code Online (Sandbox Code Playgroud)

常见文件结尾

.json

备择方案

对于您的应用程序,以下可能很重要:

  • 其他编程语言的支持
  • 读/写性能
  • 紧凑性(文件大小)

另请参见:数据序列化格式的比较

如果您正在寻找一种制作配置文件的方法,您可能希望阅读我的简短文章Python中的配置文件

  • 请注意,`force_ascii`标志默认为"True".你的json文件(以及任何其他非ascii字符)中的每个`€'都有不可读的6字节"\ u20ac"序列. (2认同)
  • 我会像500次一样投票,完成得很好 (2认同)

din*_*s66 21

对于那些试图抛弃希腊语或其他"异国情调"语言的人,例如我,但也有问题(unicode错误)与奇怪的字符,如和平符号(\ u262E)或其他通常包含在json格式数据比如Twitter,解决方案可能如下(sort_keys显然是可选的):

import codecs, json
with codecs.open('data.json', 'w', 'utf8') as f:
     f.write(json.dumps(data, sort_keys = True, ensure_ascii=False))
Run Code Online (Sandbox Code Playgroud)


ima*_*man 15

将 JSON 写入文件

import json

data = {}
data['people'] = []
data['people'].append({
    'name': 'Scott',
    'website': 'stackabuse.com',
    'from': 'Nebraska'
})
data['people'].append({
    'name': 'Larry',
    'website': 'google.com',
    'from': 'Michigan'
})
data['people'].append({
    'name': 'Tim',
    'website': 'apple.com',
    'from': 'Alabama'
})

with open('data.txt', 'w') as outfile:
    json.dump(data, outfile)
Run Code Online (Sandbox Code Playgroud)

从文件中读取 JSON

import json

with open('data.txt') as json_file:
    data = json.load(json_file)
    for p in data['people']:
        print('Name: ' + p['name'])
        print('Website: ' + p['website'])
        print('From: ' + p['from'])
        print('')
Run Code Online (Sandbox Code Playgroud)

  • 欢迎来到堆栈溢出。如果您决定回答一个已有明确答案的旧问题,那么在当天晚些时候添加新答案可能不会给您带来任何好处。如果您有一些独特的新信息,或者您确信其他答案都是错误的,请务必添加新答案,但在提出问题很长时间后提供相同的基本信息的“另一个答案”通常会获胜”不会为你赢得太多荣誉。(您显示了一些示例数据;这很好,但我不确定这是否足够,特别是当您没有显示示例数据生成的内容时。) (3认同)

ibi*_*bic 10

我没有足够的声誉来添加评论,所以我只是在这里写下我讨厌的TypeError的一些发现:

基本上,我认为它只是json.dump()Python 2中的函数中的一个错误- 它不能转储包含非ASCII字符的Python(字典/列表)数据,即使您使用encoding = 'utf-8'参数打开文件.(即不管你做什么).但是,json.dumps()适用于Python 2和3.

为了说明这一点,请跟进phihag的答案:TypeError: must be unicode, not str如果data包含非ASCII字符,则他的答案中的代码会在Python 2中出现异常.(Python 2.7.6,Debian):

import json
data = {u'\u0430\u0431\u0432\u0433\u0434': 1} #{u'?????': 1}
with open('data.txt', 'w') as outfile:
    json.dump(data, outfile)
Run Code Online (Sandbox Code Playgroud)

然而,它在Python 3中运行良好.


小智 7

使用JSON使用json.dump()json.dumps()在文件中写入数据.这样写就是将数据存储在文件中.

import json
data = [1,2,3,4,5]
with open('no.txt', 'w') as txtfile:
    json.dump(data, txtfile)
Run Code Online (Sandbox Code Playgroud)

列表中的此示例存储到文件中.


Ale*_*der 5

json.dump(data, open('data.txt', 'wb'))
Run Code Online (Sandbox Code Playgroud)

  • 这与@phihag 的答案做同样的事情,但不能保证在任何时候都有效。考虑这样的代码:`f = open('1.txt', 'w'); f.write('a'); 输入()`。运行它,然后 SYGTERM 它(`Ctrl-Z` 然后是 `kill %1` 在 linux 上,`Ctrl-Break` 在 Windows 上)。`1.txt` 将有 0 个字节。这是因为在 SYGTERM 发生的那一刻,写入被缓冲并且文件既没有刷新也没有关闭。`with` 块保证文件总是像 'try/finally' 块那样关闭,但更短。 (2认同)

gre*_*pit 5

以前的所有答案都是正确的,这是一个非常简单的例子:

#! /usr/bin/env python
import json

def write_json():
    # create a dictionary  
    student_data = {"students":[]}
    #create a list
    data_holder = student_data["students"]
    # just a counter
    counter = 0
    #loop through if you have multiple items..         
    while counter < 3:
        data_holder.append({'id':counter})
        data_holder.append({'room':counter})
        counter += 1    
    #write the file        
    file_path='/tmp/student_data.json'
    with open(file_path, 'w') as outfile:
        print("writing file to: ",file_path)
        # HERE IS WHERE THE MAGIC HAPPENS 
        json.dump(student_data, outfile)
    outfile.close()     
    print("done")

write_json()
Run Code Online (Sandbox Code Playgroud)

在此输入图像描述


Jam*_*zba 5

要使用缩进编写 JSON,请“打印漂亮”:

import json

outfile = open('data.json')
json.dump(data, outfile, indent=4)
Run Code Online (Sandbox Code Playgroud)

此外,如果您需要调试格式不正确的 JSON,并需要有用的错误消息,请使用import simplejson库,而不是import json(功能应该相同)


归档时间:

查看次数:

1336512 次

最近记录:

6 年,3 月 前