2010-10-14 65 views
5

使用應用程序引擎 - 是的,我知道所有關於django模板和其他模板引擎。讓我說我有一本字典或一個簡單的對象,我不知道它的結構,我想序列化爲HTML。python:將字典序列化爲簡單的html輸出

所以如果我有

{'data':{'id':1,'title':'home','address':{'street':'some road','city':'anycity','postal':'somepostal'}}} 

想我想是,呈現使用某種形式的列表或表格可讀的html;

data: 
    id:1 
    title:home 
    address: 
      street: some road 
      city: anycity 
      postal:somepostal 

現在我知道我能做到

for key in dict.items 
print dict[key] 

但不會潛入子值,並列出每個鍵,值對時鍵/值是一本字典 - 即地址字典。

他們是一個輕量級/快速的python模塊,可以很好地完成這個任務。或者沒有人有任何簡單的代碼,他們可以粘貼,可能會這樣做。

解決方案 這裏的所有解決方案都很有用。毫無疑問,pprint是打印字典的更穩定的手段,儘管它不能返回html附近的任何東西。雖然仍然可打印。

我結束了這個現在:

def printitems(dictObj, indent=0): 
    p=[] 
    p.append('<ul>\n') 
    for k,v in dictObj.iteritems(): 
     if isinstance(v, dict): 
      p.append('<li>'+ k+ ':') 
      p.append(printitems(v)) 
      p.append('</li>') 
     else: 
      p.append('<li>'+ k+ ':'+ v+ '</li>') 
    p.append('</ul>\n') 
    return '\n'.join(p) 

它轉換成字典無序列表這是確定現在。一些CSS,也許一點點調整應該使它可讀。

我將獎勵回答上述代碼的人,我做了一些小的更改,因爲無序列表不是嵌套。我希望所有人都同意,提供的許多解決方案都證明是有用的,但上面的代碼呈現了字典的真實html表示形式,即使是粗略的。

+1

不是一個學究,但你不能序列化你的字典,你打印(使用HTML格式)。 – Seth 2010-10-14 07:36:15

+0

@seth是的,我猜serialize這個詞是錯過使用的。 – spidee 2010-10-14 07:37:27

回答

8

通過pyfunc製成的實例可以很容易地進行修改,以產生簡單的嵌套HTML列表。

z = {'data':{'id':1,'title':'home','address':{'street':'some road','city':'anycity','postal':'somepostal'}}} 

def printItems(dictObj, indent): 
    print ' '*indent + '<ul>\n' 
    for k,v in dictObj.iteritems(): 
     if isinstance(v, dict): 
      print ' '*indent , '<li>', k, ':', '</li>' 
      printItems(v, indent+1) 
     else: 
      print ' '*indent , '<li>', k, ':', v, '</li>' 
    print ' '*indent + '</ul>\n' 

printItems(z,0) 

當然不是非常漂亮,但也許開始的地方也許。如果你想要做的只是將數據可視化,pprint模塊確實足夠好。您可以在pprint的結果上使用「pre」標記並將其放在您的網頁上。

的pprint版本將是這個樣子:

import pprint 
z = {'data':{'id':1,'title':'home','address':{'street':'some road','city':'anycity','postal':'somepostal'}}} 

print '<pre>', pprint.pformat(z), '</pre>' 

和HTML輸出是這個樣子:

{'data': {'address': {'city': 'anycity', 
         'postal': 'somepostal', 
         'street': 'some road'}, 
      'id': 1, 
      'title': 'home'}} 

這是不是漂亮,但它至少說明數據以更結構化的方式。

+0

+1這樣好多了。 – pyfunc 2010-10-14 07:25:36

+0

對不起,前標籤?我該怎麼做,你可以告訴我的代碼,使pprint返回一個字符串格式的輸出,可以傳遞給我的模板引擎。謝謝 – spidee 2010-10-14 07:29:53

4
import pprint 


pprint.pprint(yourDict) 

那麼,沒有HTML,但類似於你的for/print方法。

編輯:或使用:

niceText = pprint.pformat(yourDict) 

這會給你所有的縮進等漂亮的輸出相同的現在,你可以遍歷行,並格式化成HTML:

htmlLines = [] 
for textLine in pprint.pformat(yourDict).splitlines(): 
    htmlLines.append('<br/>%s' % textLine) # or something even nicer 
htmlText = '\n'.join(htmlLines) 
+0

好吧 - 我想把這個傳遞給html - 我該怎麼做 - 嗯,在誠實我只是希望它在一個字符串中,也許我可以傳遞給html? – spidee 2010-10-14 07:18:39

+0

這dosnt工作? ('data':{'count':'1','items':{'price':'$ 10.99','id':'1001','title':'keyword rental oct10'}} })它沒有返回格式化數據? – spidee 2010-10-14 07:42:47

+0

它在每行之後返回四行'\ n'。 – eumiro 2010-10-14 07:45:42

1

你可以使用漂亮的打印(pprint)

或者如果你想做一些進一步的顯示處理,那麼你必須自己運行dict。

被警告,代碼是粗略的,將需要大量的改進。解決方案也使用遞歸,如果遞歸深度較高,則這是不好的。

z = {'data':{'id':1,'title':'home','address':{'street':'some road','city':'anycity','postal':'somepostal', 'telephone':{'home':'xxx','offie':'yyy'}}}} 

def printItems(dictObj, indent): 
    it = dictObj.iteritems() 
    for k,v in it: 
     if isinstance(v, dict): 
      print ' '*indent , k, ':' 
      printItems(v, indent+1) 
     else: 
      print ' '*indent , k, ':', v 

printItems(z,0) 

輸出:

data : 
    address : 
    city : anycity 
    postal : somepostal 
    street : some road 
    telephone : 
    home : xxx 
    offie : yyy 
    id : 1 
    title : home 
+2

而不是'id str(type(v))'==「...」使用'type(v)== dict'或'isinstance(v,字典)(後者也適用於子類)。 – detly 2010-10-14 07:00:28

+0

如果地址碼有電話:{'home':'xxx','offie':'yyy'}它將如何處理? – spidee 2010-10-14 07:10:10

+0

@spidee:我編輯了上面的答案以包含您的數據,並以相同的方式打印。 – pyfunc 2010-10-14 07:15:49

2

看看我的實現:

def pretty_items(r, d, nametag="<strong>%s: </strong>", itemtag='<li>%s</li>', 
      valuetag="%s", blocktag=('<ul>', '</ul>')): 
if isinstance(d, dict): 
    r.append(blocktag[0]) 
    for k, v in d.iteritems(): 
     name = nametag % k 
     if isinstance(v, dict) or isinstance(v, list): 
      r.append(itemtag % name) 
      pretty_items(r, v) 
     else: 
      value = valuetag % v 
      r.append(itemtag % (name + value)) 
    r.append(blocktag[1]) 
elif isinstance(d, list): 
    r.append(blocktag[0]) 
    for i in d: 
     if isinstance(i, dict) or isinstance(i, list): 
      r.append(itemtag % " - ") 
      pretty_items(r, i) 
     else: 
      r.append(itemtag % i) 
    r.append(blocktag[1]) 

將輸出使用<ul><li>標籤以HTML格式的所有項目。也可以選擇更改標籤。然後,只需使用CSS處理縮進。

1

我需要類似的東西,但也想漂亮的打印列表,並在字典裏面列出。以下是我想出了:

def format(self, obj, indent = 1): 
    if isinstance(obj, list): 
     htmls = [] 
     for k in obj: 
      htmls.append(self.format(k,indent+1)) 

     return '[<div style="margin-left: %dem">%s</div>]' % (indent, ',<br>'.join(htmls)) 

    if isinstance(obj, dict): 
     htmls = [] 
     for k,v in obj.iteritems(): 
      htmls.append("<span style='font-style: italic; color: #888'>%s</span>: %s" % (k,self.format(v,indent+1))) 

     return '{<div style="margin-left: %dem">%s</div>}' % (indent, ',<br>'.join(htmls)) 

    return str(obj) 

然後,如果你正在使用AppEngine上的web應用,你可以做到以下幾點:

self.response.out.write(self.format(obj)) 

這是輸出的一個例子:

enter image description here

0

想象,我們有這樣的: {名稱: 「一」,孩子們:[{名: 「b」,孩子們:[]},{..},{..}]

def ConvertDictToUlLi(): 
    jsonResult = GetSomeRecursiveDict() 

    def CreateHtml(DictItem, output): 
     output = "<li>"+DictItem["name"] if jsonResult.has_key("name") else " " 
     if len(DictItem["children"]) > 0: 
      output = output + "<ul>" 
      for item in DictItem["children"]: 
       output = output + " "+CreateHtml(item, output)+" " 
      output = output + "</ul>" 
     return output+"</li>" 
    result = "<ul class='tree'>"+CreateHtml(jsonResult, "")+"</ul>" 

return result 
0

上面的例子都沒有給出好的結果,所以我寫了兩個我自己的函數,爲字典創建漂亮的html輸出。

def dict_to_html(dd, level=0): 
    """ 
    Convert dict to html using basic html tags 
    """ 
    import simplejson 
    text = '' 
    for k, v in dd.iteritems(): 
     text += '<br>' + '&nbsp;'*(4*level) + '<b>%s</b>: %s' % (k, dict_to_html(v, level+1) if isinstance(v, dict) else (simplejson.dumps(v) if isinstance(v, list) else v)) 
    return text 

def dict_to_html_ul(dd, level=0): 
    """ 
    Convert dict to html using ul/li tags 
    """ 
    import simplejson 
    text = '<ul>' 
    for k, v in dd.iteritems(): 
     text += '<li><b>%s</b>: %s</li>' % (k, dict_to_html_ul(v, level+1) if isinstance(v, dict) else (simplejson.dumps(v) if isinstance(v, list) else v)) 
    text += '</ul>' 
    return text 
0

這裏是我的版本支持列表(labels在字典鍵的詳細名稱):

def render_value(value, labels): 
    if isinstance(value, (list, tuple)): 
     return render_list(value, labels) 
    elif isinstance(value, dict): 
     return render_dict(value, labels) 
    else: 
     return value 


def render_list(lst, labels): 
    items = [ 
     '<li>%s</li>' % render_value(value, labels) 
     for value in lst 
    ] 
    return '\n'.join(['\n<ul>'] + items + ['</ul>\n']) 


def render_dict(dct, labels): 
    items = [] 
    for key, value in dct.items(): 
     if not value: continue 

     key = labels.get(key, key) 
     value = render_value(value, labels) 
     items.append('<li><b>%s</b>: %s</li>' % (key, value)) 

    return '\n'.join(['\n<ul>'] + items + ['</ul>\n'])