【问题标题】:Unable to print the resutls accordingly and write the same results in a csv file无法相应地打印结果并将相同的结果写入 csv 文件
【发布时间】:2020-04-17 09:24:18
【问题描述】:

我正在尝试根据字典中的category name 解析一些categories 的值。我选择从这本字典中解析的类别名称现在是Interior FeaturesSpaces and Amenities。以下脚本可以解析它们,但是当我尝试打印它们时,该输出的对齐变得混乱,当我编写它们时,这显然会在 csv 文件中产生类似的影响。

如何打印结果并以正确的方式将其写入 csv 文件?

以下内容供您参考:

[{'categoryGroupName': 'Interior Features', 'categories': [{'categoryName': 'Bedrooms', 'categoryFacts': [{'factLabel': 'Beds', 'factValue': '3'}, {'factLabel': 'Master bedroom location', 'factValue': 'Main'}]}, {'categoryName': 'Kitchen', 'categoryFacts': [{'factLabel': 'Kitchen location', 'factValue': 'Main'}]}, {'categoryName': 'Other Rooms', 'categoryFacts': [{'factLabel': 'Dining room location', 'factValue': 'Main'}, {'factLabel': 'Living room location', 'factValue': 'Main'}, {'factLabel': 'Utility room location', 'factValue': 'Lower'}]}, {'categoryName': 'Heating and Cooling', 'categoryFacts': [{'factLabel': 'Heating', 'factValue': 'Forced air'}, {'factLabel': 'Heating', 'factValue': 'Gas'}, {'factLabel': 'Heating and cooling', 'factValue': '90%+ High Efficiency, Forced Air'}]}, {'categoryName': 'Basement', 'categoryFacts': [{'factLabel': None, 'factValue': 'Partially finished'}, {'factLabel': None, 'factValue': '900 sqft basement'}, {'factLabel': 'Basement', 'factValue': 'Partially Finished'}]}, {'categoryName': 'Attic', 'categoryFacts': [{'factLabel': None, 'factValue': 'Attic'}]}, {'categoryName': 'Appliances', 'categoryFacts': [{'factLabel': 'Appliances included', 'factValue': 'Dishwasher, Dryer, Microwave, Range / Oven, Refrigerator, Washer'}, {'factLabel': 'Appliances that stay', 'factValue': 'Range/Oven, Dishwasher, Refrigerator, Washer, Dryer'}]}, {'categoryName': 'Flooring', 'categoryFacts': [{'factLabel': 'Floor size', 'factValue': '2,070 sqft'}, {'factLabel': 'Flooring', 'factValue': 'Carpet, Hardwood, Tile'}, {'factLabel': 'Floor covering', 'factValue': 'Hardwood, Laminate, Wall to Wall Carpet'}]}, {'categoryName': 'Other Interior Features', 'categoryFacts': [{'factLabel': 'Addition size', 'factValue': '900'}, {'factLabel': None, 'factValue': 'Fireplace'}, {'factLabel': None, 'factValue': 'Ceiling Fan'}, {'factLabel': 'Features', 'factValue': 'Dbl Pane/Storm Windw, Dining Room, Security System, Ceiling Fan(s), Hot Tub/Spa'}]}]}, {'categoryGroupName': 'Building', 'categories': [{'categoryName': 'Other Building Features', 'categoryFacts': [{'factLabel': 'Building info', 'factValue': 'Built On Lot'}]}]}, {'categoryGroupName': 'Spaces and Amenities', 'categories': [{'categoryName': 'Size', 'categoryFacts': [{'factLabel': 'Unit count', 'factValue': '1'}]}, {'categoryName': 'Spaces', 'categoryFacts': [{'factLabel': None, 'factValue': 'Hot Tub/Spa'}]}, {'categoryName': 'Amenities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Security System'}]}]}, {'categoryGroupName': 'Construction', 'categories': [{'categoryName': 'Type and Style', 'categoryFacts': [{'factLabel': 'Structure type', 'factValue': 'Craftsman'}, {'factLabel': None, 'factValue': 'Single Family'}, {'factLabel': 'Architecture', 'factValue': 'Craftsman'}, {'factLabel': 'Entrance level', 'factValue': 'Main'}, {'factLabel': 'Style', 'factValue': '16 - 1 Story w/Bsmnt.'}]}, {'categoryName': 'Materials', 'categoryFacts': [{'factLabel': 'Roof type', 'factValue': 'Composition'}, {'factLabel': 'Exterior material', 'factValue': 'Wood'}, {'factLabel': 'Roof', 'factValue': 'Composition'}, {'factLabel': 'Foundation', 'factValue': 'Poured Concrete'}]}, {'categoryName': 'Dates', 'categoryFacts': [{'factLabel': None, 'factValue': 'Built in 1916'}]}, {'categoryName': 'Other Construction Features', 'categoryFacts': [{'factLabel': 'Stories', 'factValue': '1'}]}]}, {'categoryGroupName': 'Exterior Features', 'categories': [{'categoryName': 'Patio', 'categoryFacts': [{'factLabel': None, 'factValue': 'Deck'}]}, {'categoryName': 'Yard', 'categoryFacts': [{'factLabel': None, 'factValue': 'Fenced Yard'}, {'factLabel': None, 'factValue': 'Garden'}]}, {'categoryName': 'View Type', 'categoryFacts': [{'factLabel': 'View', 'factValue': 'Mountain'}, {'factLabel': 'View', 'factValue': 'Territorial, See Remarks'}]}, {'categoryName': 'Lot', 'categoryFacts': [{'factLabel': 'Lot', 'factValue': '4,000 sqft'}, {'factLabel': 'Lot topography/vegetation', 'factValue': 'Level, Steep Slope'}, {'factLabel': 'Lot details', 'factValue': 'Paved Street, Sidewalk, Curbs'}]}, {'categoryName': 'Other Exterior Features', 'categoryFacts': [{'factLabel': 'Parcel #', 'factValue': '6610001005'}, {'factLabel': 'Exterior', 'factValue': 'Wood'}]}]}, {'categoryGroupName': 'Community and Neighborhood', 'categories': [{'categoryName': 'Schools', 'categoryFacts': [{'factLabel': 'Elementary school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'Middle school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'High school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'School district', 'factValue': 'Seattle'}]}, {'categoryName': 'Transportation', 'categoryFacts': [{'factLabel': 'Bus line nearby', 'factValue': 'Y'}]}]}, {'categoryGroupName': 'Parking', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Parking', 'factValue': 'Attached Garage, 1 space, 290 sqft garage'}, {'factLabel': 'Parking type', 'factValue': 'Garage-Attached, Off Street'}]}]}, {'categoryGroupName': 'Utilities', 'categories': [{'categoryName': 'Utilities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Cable Ready'}, {'factLabel': 'Sewer', 'factValue': 'Sewer Connected'}, {'factLabel': 'Water source', 'factValue': 'Public'}]}, {'categoryName': 'Green Energy', 'categoryFacts': [{'factLabel': 'Energy source', 'factValue': 'Natural Gas, Solar (Unspecified)'}]}]}, {'categoryGroupName': 'Other', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Last sold', 'factValue': 'Dec 2019 for $900,000'}, {'factLabel': 'Last sale price/sqft', 'factValue': '$435'}, {'factLabel': 'Property type', 'factValue': 'RESI'}, {'factLabel': 'Possesion', 'factValue': 'Closing'}, {'factLabel': 'Form 17', 'factValue': 'Provided'}, {'factLabel': 'Potential terms', 'factValue': 'Cash Out, Conventional'}, {'factLabel': 'Site features', 'factValue': 'Cable TV, Deck, Fenced-Partially, Gas Available, Hot Tub/Spa'}, {'factLabel': 'Offers', 'factValue': 'Reviewed on receipt'}, {'factLabel': 'Commission', 'factValue': '2.5%'}]}]}, {'categoryGroupName': 'Activity On Zillow', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Views since listing', 'factValue': '77'}, {'factLabel': None, 'factValue': '1 shopper saved this home'}]}]}]

我尝试过的脚本:

desc = [{'categoryGroupName': 'Interior Features', 'categories': [{'categoryName': 'Bedrooms', 'categoryFacts': [{'factLabel': 'Beds', 'factValue': '3'}, {'factLabel': 'Master bedroom location', 'factValue': 'Main'}]}, {'categoryName': 'Kitchen', 'categoryFacts': [{'factLabel': 'Kitchen location', 'factValue': 'Main'}]}, {'categoryName': 'Other Rooms', 'categoryFacts': [{'factLabel': 'Dining room location', 'factValue': 'Main'}, {'factLabel': 'Living room location', 'factValue': 'Main'}, {'factLabel': 'Utility room location', 'factValue': 'Lower'}]}, {'categoryName': 'Heating and Cooling', 'categoryFacts': [{'factLabel': 'Heating', 'factValue': 'Forced air'}, {'factLabel': 'Heating', 'factValue': 'Gas'}, {'factLabel': 'Heating and cooling', 'factValue': '90%+ High Efficiency, Forced Air'}]}, {'categoryName': 'Basement', 'categoryFacts': [{'factLabel': None, 'factValue': 'Partially finished'}, {'factLabel': None, 'factValue': '900 sqft basement'}, {'factLabel': 'Basement', 'factValue': 'Partially Finished'}]}, {'categoryName': 'Attic', 'categoryFacts': [{'factLabel': None, 'factValue': 'Attic'}]}, {'categoryName': 'Appliances', 'categoryFacts': [{'factLabel': 'Appliances included', 'factValue': 'Dishwasher, Dryer, Microwave, Range / Oven, Refrigerator, Washer'}, {'factLabel': 'Appliances that stay', 'factValue': 'Range/Oven, Dishwasher, Refrigerator, Washer, Dryer'}]}, {'categoryName': 'Flooring', 'categoryFacts': [{'factLabel': 'Floor size', 'factValue': '2,070 sqft'}, {'factLabel': 'Flooring', 'factValue': 'Carpet, Hardwood, Tile'}, {'factLabel': 'Floor covering', 'factValue': 'Hardwood, Laminate, Wall to Wall Carpet'}]}, {'categoryName': 'Other Interior Features', 'categoryFacts': [{'factLabel': 'Addition size', 'factValue': '900'}, {'factLabel': None, 'factValue': 'Fireplace'}, {'factLabel': None, 'factValue': 'Ceiling Fan'}, {'factLabel': 'Features', 'factValue': 'Dbl Pane/Storm Windw, Dining Room, Security System, Ceiling Fan(s), Hot Tub/Spa'}]}]}, {'categoryGroupName': 'Building', 'categories': [{'categoryName': 'Other Building Features', 'categoryFacts': [{'factLabel': 'Building info', 'factValue': 'Built On Lot'}]}]}, {'categoryGroupName': 'Spaces and Amenities', 'categories': [{'categoryName': 'Size', 'categoryFacts': [{'factLabel': 'Unit count', 'factValue': '1'}]}, {'categoryName': 'Spaces', 'categoryFacts': [{'factLabel': None, 'factValue': 'Hot Tub/Spa'}]}, {'categoryName': 'Amenities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Security System'}]}]}, {'categoryGroupName': 'Construction', 'categories': [{'categoryName': 'Type and Style', 'categoryFacts': [{'factLabel': 'Structure type', 'factValue': 'Craftsman'}, {'factLabel': None, 'factValue': 'Single Family'}, {'factLabel': 'Architecture', 'factValue': 'Craftsman'}, {'factLabel': 'Entrance level', 'factValue': 'Main'}, {'factLabel': 'Style', 'factValue': '16 - 1 Story w/Bsmnt.'}]}, {'categoryName': 'Materials', 'categoryFacts': [{'factLabel': 'Roof type', 'factValue': 'Composition'}, {'factLabel': 'Exterior material', 'factValue': 'Wood'}, {'factLabel': 'Roof', 'factValue': 'Composition'}, {'factLabel': 'Foundation', 'factValue': 'Poured Concrete'}]}, {'categoryName': 'Dates', 'categoryFacts': [{'factLabel': None, 'factValue': 'Built in 1916'}]}, {'categoryName': 'Other Construction Features', 'categoryFacts': [{'factLabel': 'Stories', 'factValue': '1'}]}]}, {'categoryGroupName': 'Exterior Features', 'categories': [{'categoryName': 'Patio', 'categoryFacts': [{'factLabel': None, 'factValue': 'Deck'}]}, {'categoryName': 'Yard', 'categoryFacts': [{'factLabel': None, 'factValue': 'Fenced Yard'}, {'factLabel': None, 'factValue': 'Garden'}]}, {'categoryName': 'View Type', 'categoryFacts': [{'factLabel': 'View', 'factValue': 'Mountain'}, {'factLabel': 'View', 'factValue': 'Territorial, See Remarks'}]}, {'categoryName': 'Lot', 'categoryFacts': [{'factLabel': 'Lot', 'factValue': '4,000 sqft'}, {'factLabel': 'Lot topography/vegetation', 'factValue': 'Level, Steep Slope'}, {'factLabel': 'Lot details', 'factValue': 'Paved Street, Sidewalk, Curbs'}]}, {'categoryName': 'Other Exterior Features', 'categoryFacts': [{'factLabel': 'Parcel #', 'factValue': '6610001005'}, {'factLabel': 'Exterior', 'factValue': 'Wood'}]}]}, {'categoryGroupName': 'Community and Neighborhood', 'categories': [{'categoryName': 'Schools', 'categoryFacts': [{'factLabel': 'Elementary school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'Middle school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'High school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'School district', 'factValue': 'Seattle'}]}, {'categoryName': 'Transportation', 'categoryFacts': [{'factLabel': 'Bus line nearby', 'factValue': 'Y'}]}]}, {'categoryGroupName': 'Parking', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Parking', 'factValue': 'Attached Garage, 1 space, 290 sqft garage'}, {'factLabel': 'Parking type', 'factValue': 'Garage-Attached, Off Street'}]}]}, {'categoryGroupName': 'Utilities', 'categories': [{'categoryName': 'Utilities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Cable Ready'}, {'factLabel': 'Sewer', 'factValue': 'Sewer Connected'}, {'factLabel': 'Water source', 'factValue': 'Public'}]}, {'categoryName': 'Green Energy', 'categoryFacts': [{'factLabel': 'Energy source', 'factValue': 'Natural Gas, Solar (Unspecified)'}]}]}, {'categoryGroupName': 'Other', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Last sold', 'factValue': 'Dec 2019 for $900,000'}, {'factLabel': 'Last sale price/sqft', 'factValue': '$435'}, {'factLabel': 'Property type', 'factValue': 'RESI'}, {'factLabel': 'Possesion', 'factValue': 'Closing'}, {'factLabel': 'Form 17', 'factValue': 'Provided'}, {'factLabel': 'Potential terms', 'factValue': 'Cash Out, Conventional'}, {'factLabel': 'Site features', 'factValue': 'Cable TV, Deck, Fenced-Partially, Gas Available, Hot Tub/Spa'}, {'factLabel': 'Offers', 'factValue': 'Reviewed on receipt'}, {'factLabel': 'Commission', 'factValue': '2.5%'}]}]}, {'categoryGroupName': 'Activity On Zillow', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Views since listing', 'factValue': '77'}, {'factLabel': None, 'factValue': '1 shopper saved this home'}]}]}]

name = "property in somewhere"

for elem in desc:

    if elem['categoryGroupName']=='Interior Features':
        interior_features = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        interior_features = str(interior_features).replace("{","").replace("}","").replace("'","")
    else:
        interior_features = ""

    if elem['categoryGroupName']=='Spaces and Amenities':
        space_amenities = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        space_amenities = str(space_amenities).replace("{","").replace("}","").replace("'","")
    else:
        space_amenities = ""

    print(name,interior_features,space_amenities)

我得到的结果:

property in somewhere Beds: 3, Master bedroom location: Main, Kitchen location: Main, Dining room location: Main, Living room location: Main, Utility room location: Lower, Heating: Gas, Heating and cooling: 90%+ High Efficiency, Forced Air, None: Ceiling Fan, Basement: Partially Finished, Appliances included: Dishwasher, Dryer, Microwave, Range / Oven, Refrigerator, Washer, Appliances that stay: Range/Oven, Dishwasher, Refrigerator, Washer, Dryer, Floor size: 2,070 sqft, Flooring: Carpet, Hardwood, Tile, Floor covering: Hardwood, Laminate, Wall to Wall Carpet, Addition size: 900, Features: Dbl Pane/Storm Windw, Dining Room, Security System, Ceiling Fan(s), Hot Tub/Spa 
property in somewhere  
property in somewhere  Unit count: 1, None: Security System
property in somewhere  
property in somewhere  
property in somewhere  
property in somewhere  
property in somewhere  
property in somewhere  
property in somewhere

在上面的输出中你可以看到这行property in somewhere 已经被打印了好几次,而它应该被打印一次。这行Unit count: 1, None: Security System 应该在第三列,而它被放置了一些不需要的区域。

底线是上面的脚本应该打印一次结果,但由于 for 循环,它会打印多次。

预期输出(在此处粘贴变量名称而不是它们的值,以使您了解对齐方式)。更清楚一点 - b 行、c 行等没有结果。结果应打印一次,并仅限于 A1 行、B1 行和 C1 行。期间。

Column A    Column B             Column C
name        interior_features    space_amenities

【问题讨论】:

  • @robots.txt--'property in something'被多次打印的原因是你有10个类别,即:['Interior Features','Building','Spaces andities','建筑”、“外部特征”、“社区和邻里”、“停车”、“公用事业”、“其他”、“Zillow 上的活动”]。其中只有两个与您的过滤器匹配并有数据,而其他则打印 internal_featues 和 space_amenities 的空字符串。
  • 嗨 robots.txt,很高兴再次见到你。如果我理解正确,每个desc 列表预计只有一个interior_features 项目和一个space_amenities 项目。如果是这样,您可以创建一个包含 name 值的列表,并在找到 interior_featuresspace_amenities 值时将其添加到列表中。在循环结束时,您应该有一个包含三个项目的列表:[name, interior_features, space_amenities],您可以打印或保存到文件。如果有不清楚的地方,或者我误解了问题,请告诉我。
  • 嗨@t.m.adam,很高兴在循环中找到你。如果您查看this link,您会发现我的修正方法符合您的建议。请通读。谢谢。
  • 好的,在这种情况下,您可以使用带有 N/A 作为默认值的字典(例如:rows = {'name': name, 'interior_features':'N/A', 'space_amenities':'N/A', 'imaginary_stuff':'N/A'} )。当您找到一个项目时,将其添加到字典中;如果没有项目,则字典键将具有默认值 - N/A。您可以使用dict.values() 获取列表中的字典值。
  • 这个想法似乎很有前途@t.m.adam。问题是我真的找不到关于如何在脚本中实现它的任何想法,因为在使用字典内容时我已经落后了。

标签: python json python-3.x csv dictionary


【解决方案1】:

如果我理解正确,目标是从desc 中的项目中获取某些值。每个值可能出现一次或根本不出现 - 在这种情况下,结果应该是“N/A”。因此,您可以使用具有 N/A 默认值的字典,然后将它们替换为在 desc 列表中找到的值。

desc = [{'categoryGroupName': 'Interior Features', 'categories': [{'categoryName': 'Bedrooms', 'categoryFacts': [{'factLabel': 'Beds', 'factValue': '3'}, {'factLabel': 'Master bedroom location', 'factValue': 'Main'}]}, {'categoryName': 'Kitchen', 'categoryFacts': [{'factLabel': 'Kitchen location', 'factValue': 'Main'}]}, {'categoryName': 'Other Rooms', 'categoryFacts': [{'factLabel': 'Dining room location', 'factValue': 'Main'}, {'factLabel': 'Living room location', 'factValue': 'Main'}, {'factLabel': 'Utility room location', 'factValue': 'Lower'}]}, {'categoryName': 'Heating and Cooling', 'categoryFacts': [{'factLabel': 'Heating', 'factValue': 'Forced air'}, {'factLabel': 'Heating', 'factValue': 'Gas'}, {'factLabel': 'Heating and cooling', 'factValue': '90%+ High Efficiency, Forced Air'}]}, {'categoryName': 'Basement', 'categoryFacts': [{'factLabel': None, 'factValue': 'Partially finished'}, {'factLabel': None, 'factValue': '900 sqft basement'}, {'factLabel': 'Basement', 'factValue': 'Partially Finished'}]}, {'categoryName': 'Attic', 'categoryFacts': [{'factLabel': None, 'factValue': 'Attic'}]}, {'categoryName': 'Appliances', 'categoryFacts': [{'factLabel': 'Appliances included', 'factValue': 'Dishwasher, Dryer, Microwave, Range / Oven, Refrigerator, Washer'}, {'factLabel': 'Appliances that stay', 'factValue': 'Range/Oven, Dishwasher, Refrigerator, Washer, Dryer'}]}, {'categoryName': 'Flooring', 'categoryFacts': [{'factLabel': 'Floor size', 'factValue': '2,070 sqft'}, {'factLabel': 'Flooring', 'factValue': 'Carpet, Hardwood, Tile'}, {'factLabel': 'Floor covering', 'factValue': 'Hardwood, Laminate, Wall to Wall Carpet'}]}, {'categoryName': 'Other Interior Features', 'categoryFacts': [{'factLabel': 'Addition size', 'factValue': '900'}, {'factLabel': None, 'factValue': 'Fireplace'}, {'factLabel': None, 'factValue': 'Ceiling Fan'}, {'factLabel': 'Features', 'factValue': 'Dbl Pane/Storm Windw, Dining Room, Security System, Ceiling Fan(s), Hot Tub/Spa'}]}]}, {'categoryGroupName': 'Building', 'categories': [{'categoryName': 'Other Building Features', 'categoryFacts': [{'factLabel': 'Building info', 'factValue': 'Built On Lot'}]}]}, {'categoryGroupName': 'Spaces and Amenities', 'categories': [{'categoryName': 'Size', 'categoryFacts': [{'factLabel': 'Unit count', 'factValue': '1'}]}, {'categoryName': 'Spaces', 'categoryFacts': [{'factLabel': None, 'factValue': 'Hot Tub/Spa'}]}, {'categoryName': 'Amenities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Security System'}]}]}, {'categoryGroupName': 'Construction', 'categories': [{'categoryName': 'Type and Style', 'categoryFacts': [{'factLabel': 'Structure type', 'factValue': 'Craftsman'}, {'factLabel': None, 'factValue': 'Single Family'}, {'factLabel': 'Architecture', 'factValue': 'Craftsman'}, {'factLabel': 'Entrance level', 'factValue': 'Main'}, {'factLabel': 'Style', 'factValue': '16 - 1 Story w/Bsmnt.'}]}, {'categoryName': 'Materials', 'categoryFacts': [{'factLabel': 'Roof type', 'factValue': 'Composition'}, {'factLabel': 'Exterior material', 'factValue': 'Wood'}, {'factLabel': 'Roof', 'factValue': 'Composition'}, {'factLabel': 'Foundation', 'factValue': 'Poured Concrete'}]}, {'categoryName': 'Dates', 'categoryFacts': [{'factLabel': None, 'factValue': 'Built in 1916'}]}, {'categoryName': 'Other Construction Features', 'categoryFacts': [{'factLabel': 'Stories', 'factValue': '1'}]}]}, {'categoryGroupName': 'Exterior Features', 'categories': [{'categoryName': 'Patio', 'categoryFacts': [{'factLabel': None, 'factValue': 'Deck'}]}, {'categoryName': 'Yard', 'categoryFacts': [{'factLabel': None, 'factValue': 'Fenced Yard'}, {'factLabel': None, 'factValue': 'Garden'}]}, {'categoryName': 'View Type', 'categoryFacts': [{'factLabel': 'View', 'factValue': 'Mountain'}, {'factLabel': 'View', 'factValue': 'Territorial, See Remarks'}]}, {'categoryName': 'Lot', 'categoryFacts': [{'factLabel': 'Lot', 'factValue': '4,000 sqft'}, {'factLabel': 'Lot topography/vegetation', 'factValue': 'Level, Steep Slope'}, {'factLabel': 'Lot details', 'factValue': 'Paved Street, Sidewalk, Curbs'}]}, {'categoryName': 'Other Exterior Features', 'categoryFacts': [{'factLabel': 'Parcel #', 'factValue': '6610001005'}, {'factLabel': 'Exterior', 'factValue': 'Wood'}]}]}, {'categoryGroupName': 'Community and Neighborhood', 'categories': [{'categoryName': 'Schools', 'categoryFacts': [{'factLabel': 'Elementary school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'Middle school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'High school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'School district', 'factValue': 'Seattle'}]}, {'categoryName': 'Transportation', 'categoryFacts': [{'factLabel': 'Bus line nearby', 'factValue': 'Y'}]}]}, {'categoryGroupName': 'Parking', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Parking', 'factValue': 'Attached Garage, 1 space, 290 sqft garage'}, {'factLabel': 'Parking type', 'factValue': 'Garage-Attached, Off Street'}]}]}, {'categoryGroupName': 'Utilities', 'categories': [{'categoryName': 'Utilities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Cable Ready'}, {'factLabel': 'Sewer', 'factValue': 'Sewer Connected'}, {'factLabel': 'Water source', 'factValue': 'Public'}]}, {'categoryName': 'Green Energy', 'categoryFacts': [{'factLabel': 'Energy source', 'factValue': 'Natural Gas, Solar (Unspecified)'}]}]}, {'categoryGroupName': 'Other', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Last sold', 'factValue': 'Dec 2019 for $900,000'}, {'factLabel': 'Last sale price/sqft', 'factValue': '$435'}, {'factLabel': 'Property type', 'factValue': 'RESI'}, {'factLabel': 'Possesion', 'factValue': 'Closing'}, {'factLabel': 'Form 17', 'factValue': 'Provided'}, {'factLabel': 'Potential terms', 'factValue': 'Cash Out, Conventional'}, {'factLabel': 'Site features', 'factValue': 'Cable TV, Deck, Fenced-Partially, Gas Available, Hot Tub/Spa'}, {'factLabel': 'Offers', 'factValue': 'Reviewed on receipt'}, {'factLabel': 'Commission', 'factValue': '2.5%'}]}]}, {'categoryGroupName': 'Activity On Zillow', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Views since listing', 'factValue': '77'}, {'factLabel': None, 'factValue': '1 shopper saved this home'}]}]}]
name = "property in somewhere"
rows = {'name': name, 'interior_features':'N/A', 'space_amenities':'N/A', 'imaginary_stuff':'N/A'}

for elem in desc:
    if elem['categoryGroupName']=='Interior Features':
        interior_features = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        interior_features = str(interior_features).replace("{","").replace("}","").replace("'","")
        rows['interior_features'] = interior_features

    if elem['categoryGroupName']=='Imaginary Stuff':
        imaginary_stuff = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        imaginary_stuff = str(imaginary_stuff).replace("{","").replace("}","").replace("'","")   
        rows['imaginary_stuff'] = imaginary_stuff

    if elem['categoryGroupName']=='Spaces and Amenities':
        space_amenities = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        space_amenities = str(space_amenities).replace("{","").replace("}","").replace("'","")
        rows['space_amenities'] = space_amenities 

print(rows)

但是,如果一个值出现不止一次,上面的代码可能会出现问题,因为它只会存储最后一个值。在这种情况下,我们可以使用空列表作为 rows 字典的值。然后附加在desc 列表中找到的值。最后,如果一个列表有值,则将它们加入一个字符串,如果没有,则将空列表替换为“N/A”。

desc = [{'categoryGroupName': 'Interior Features', 'categories': [{'categoryName': 'Bedrooms', 'categoryFacts': [{'factLabel': 'Beds', 'factValue': '3'}, {'factLabel': 'Master bedroom location', 'factValue': 'Main'}]}, {'categoryName': 'Kitchen', 'categoryFacts': [{'factLabel': 'Kitchen location', 'factValue': 'Main'}]}, {'categoryName': 'Other Rooms', 'categoryFacts': [{'factLabel': 'Dining room location', 'factValue': 'Main'}, {'factLabel': 'Living room location', 'factValue': 'Main'}, {'factLabel': 'Utility room location', 'factValue': 'Lower'}]}, {'categoryName': 'Heating and Cooling', 'categoryFacts': [{'factLabel': 'Heating', 'factValue': 'Forced air'}, {'factLabel': 'Heating', 'factValue': 'Gas'}, {'factLabel': 'Heating and cooling', 'factValue': '90%+ High Efficiency, Forced Air'}]}, {'categoryName': 'Basement', 'categoryFacts': [{'factLabel': None, 'factValue': 'Partially finished'}, {'factLabel': None, 'factValue': '900 sqft basement'}, {'factLabel': 'Basement', 'factValue': 'Partially Finished'}]}, {'categoryName': 'Attic', 'categoryFacts': [{'factLabel': None, 'factValue': 'Attic'}]}, {'categoryName': 'Appliances', 'categoryFacts': [{'factLabel': 'Appliances included', 'factValue': 'Dishwasher, Dryer, Microwave, Range / Oven, Refrigerator, Washer'}, {'factLabel': 'Appliances that stay', 'factValue': 'Range/Oven, Dishwasher, Refrigerator, Washer, Dryer'}]}, {'categoryName': 'Flooring', 'categoryFacts': [{'factLabel': 'Floor size', 'factValue': '2,070 sqft'}, {'factLabel': 'Flooring', 'factValue': 'Carpet, Hardwood, Tile'}, {'factLabel': 'Floor covering', 'factValue': 'Hardwood, Laminate, Wall to Wall Carpet'}]}, {'categoryName': 'Other Interior Features', 'categoryFacts': [{'factLabel': 'Addition size', 'factValue': '900'}, {'factLabel': None, 'factValue': 'Fireplace'}, {'factLabel': None, 'factValue': 'Ceiling Fan'}, {'factLabel': 'Features', 'factValue': 'Dbl Pane/Storm Windw, Dining Room, Security System, Ceiling Fan(s), Hot Tub/Spa'}]}]}, {'categoryGroupName': 'Building', 'categories': [{'categoryName': 'Other Building Features', 'categoryFacts': [{'factLabel': 'Building info', 'factValue': 'Built On Lot'}]}]}, {'categoryGroupName': 'Spaces and Amenities', 'categories': [{'categoryName': 'Size', 'categoryFacts': [{'factLabel': 'Unit count', 'factValue': '1'}]}, {'categoryName': 'Spaces', 'categoryFacts': [{'factLabel': None, 'factValue': 'Hot Tub/Spa'}]}, {'categoryName': 'Amenities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Security System'}]}]}, {'categoryGroupName': 'Construction', 'categories': [{'categoryName': 'Type and Style', 'categoryFacts': [{'factLabel': 'Structure type', 'factValue': 'Craftsman'}, {'factLabel': None, 'factValue': 'Single Family'}, {'factLabel': 'Architecture', 'factValue': 'Craftsman'}, {'factLabel': 'Entrance level', 'factValue': 'Main'}, {'factLabel': 'Style', 'factValue': '16 - 1 Story w/Bsmnt.'}]}, {'categoryName': 'Materials', 'categoryFacts': [{'factLabel': 'Roof type', 'factValue': 'Composition'}, {'factLabel': 'Exterior material', 'factValue': 'Wood'}, {'factLabel': 'Roof', 'factValue': 'Composition'}, {'factLabel': 'Foundation', 'factValue': 'Poured Concrete'}]}, {'categoryName': 'Dates', 'categoryFacts': [{'factLabel': None, 'factValue': 'Built in 1916'}]}, {'categoryName': 'Other Construction Features', 'categoryFacts': [{'factLabel': 'Stories', 'factValue': '1'}]}]}, {'categoryGroupName': 'Exterior Features', 'categories': [{'categoryName': 'Patio', 'categoryFacts': [{'factLabel': None, 'factValue': 'Deck'}]}, {'categoryName': 'Yard', 'categoryFacts': [{'factLabel': None, 'factValue': 'Fenced Yard'}, {'factLabel': None, 'factValue': 'Garden'}]}, {'categoryName': 'View Type', 'categoryFacts': [{'factLabel': 'View', 'factValue': 'Mountain'}, {'factLabel': 'View', 'factValue': 'Territorial, See Remarks'}]}, {'categoryName': 'Lot', 'categoryFacts': [{'factLabel': 'Lot', 'factValue': '4,000 sqft'}, {'factLabel': 'Lot topography/vegetation', 'factValue': 'Level, Steep Slope'}, {'factLabel': 'Lot details', 'factValue': 'Paved Street, Sidewalk, Curbs'}]}, {'categoryName': 'Other Exterior Features', 'categoryFacts': [{'factLabel': 'Parcel #', 'factValue': '6610001005'}, {'factLabel': 'Exterior', 'factValue': 'Wood'}]}]}, {'categoryGroupName': 'Community and Neighborhood', 'categories': [{'categoryName': 'Schools', 'categoryFacts': [{'factLabel': 'Elementary school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'Middle school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'High school', 'factValue': 'Buyer To Verify'}, {'factLabel': 'School district', 'factValue': 'Seattle'}]}, {'categoryName': 'Transportation', 'categoryFacts': [{'factLabel': 'Bus line nearby', 'factValue': 'Y'}]}]}, {'categoryGroupName': 'Parking', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Parking', 'factValue': 'Attached Garage, 1 space, 290 sqft garage'}, {'factLabel': 'Parking type', 'factValue': 'Garage-Attached, Off Street'}]}]}, {'categoryGroupName': 'Utilities', 'categories': [{'categoryName': 'Utilities', 'categoryFacts': [{'factLabel': None, 'factValue': 'Cable Ready'}, {'factLabel': 'Sewer', 'factValue': 'Sewer Connected'}, {'factLabel': 'Water source', 'factValue': 'Public'}]}, {'categoryName': 'Green Energy', 'categoryFacts': [{'factLabel': 'Energy source', 'factValue': 'Natural Gas, Solar (Unspecified)'}]}]}, {'categoryGroupName': 'Other', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Last sold', 'factValue': 'Dec 2019 for $900,000'}, {'factLabel': 'Last sale price/sqft', 'factValue': '$435'}, {'factLabel': 'Property type', 'factValue': 'RESI'}, {'factLabel': 'Possesion', 'factValue': 'Closing'}, {'factLabel': 'Form 17', 'factValue': 'Provided'}, {'factLabel': 'Potential terms', 'factValue': 'Cash Out, Conventional'}, {'factLabel': 'Site features', 'factValue': 'Cable TV, Deck, Fenced-Partially, Gas Available, Hot Tub/Spa'}, {'factLabel': 'Offers', 'factValue': 'Reviewed on receipt'}, {'factLabel': 'Commission', 'factValue': '2.5%'}]}]}, {'categoryGroupName': 'Activity On Zillow', 'categories': [{'categoryName': '', 'categoryFacts': [{'factLabel': 'Views since listing', 'factValue': '77'}, {'factLabel': None, 'factValue': '1 shopper saved this home'}]}]}]
name = "property in somewhere"
rows = {'name': name, 'interior_features':[], 'space_amenities':[], 'imaginary_stuff':[]}

for elem in desc:
    if elem['categoryGroupName']=='Interior Features' or elem['categoryGroupName']== 'Spaces and Amenities':
        interior_features = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        interior_features = str(interior_features).replace("{","").replace("}","").replace("'","")
        rows['interior_features'].append(interior_features)

    if elem['categoryGroupName']=='Imaginary Stuff':
        imaginary_stuff = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        imaginary_stuff = str(imaginary_stuff).replace("{","").replace("}","").replace("'","")   
        rows['imaginary_stuff'].append(imaginary_stuff)

    if elem['categoryGroupName']=='Spaces and Amenities':
        space_amenities = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
        space_amenities = str(space_amenities).replace("{","").replace("}","").replace("'","")
        rows['space_amenities'].append(space_amenities)


separator = ' | '
rows = {k: separator.join(v) if v else 'N/A' for k,v in rows.items()}
print(rows)

如果您希望将rows 字典转换为列表,您可以使用rows.values()。您还可以使用csv.DictWriter(),这样您就可以将结果写入文件,而无需将其转换为列表。

import csv

with open('file.csv', 'w', encoding='utf-8', newline='') as f:
    w = csv.DictWriter(f, rows.keys())
    w.writeheader()
    w.writerow(rows)

【讨论】:

  • 最后我已经能够说服你在一个python问题中写一个答案。保持冷静,直到下一个麻烦。
  • 哈! 2020 年最美好的祝愿!
  • 你也一样。谢谢。
  • 忘了问一个非常不相关的问题。你有选择深入挖掘scrapy吗?
  • 不,我根本不使用scrapy。现在,我也有一个问题。一个值是否可以在desc 列表中多次出现?如果是这样,我的代码可能有问题,因为 rows 键将只有最后一个值。
【解决方案2】:

您的代码的两个模块:

(1) 根据每列的最大宽度左对齐每个字段

(2) 不要打印与所需类别不匹配的类别(即返回空特征)

def features(elem):
    " Gets features (interior and space) for current element "
    if elem['categoryGroupName']=='Interior Features':
            interior_features = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
            interior_features = str(interior_features).replace("{","").replace("}","").replace("'","")
    else:
        interior_features = ""

    if elem['categoryGroupName']=='Spaces and Amenities':
            space_amenities = {curr['factLabel']: curr['factValue'] for i in elem['categories'] for curr in i['categoryFacts']}
            space_amenities = str(space_amenities).replace("{","").replace("}","").replace("'","")
    else:
        space_amenities = ""

    return interior_features, space_amenities

def format_data(row, col_widths):
    " Format row data so it has the right column width "
    # align based upon max width of each column
    # columns are tab separated so this can act as a CSV file
    return "/t".join(word.ljust(col_widths[i]) for i, word in enumerate(row))

# Widths to use for fields
feature_widths = [list(map(len, features(elem))) for elem in desc]
field0_max = len('property in somewhere')
field1_max = max(i[0] for i in feature_widths)
field2_max = max(i[1] for i in feature_widths)
col_widths = [field0_max+2, field1_max + 2, field2_max+2]

# Print header
with open('test.txt', 'w') as txtfile:
    # Write header
    row = ["property in somewhere", 'interior_features', 'space_amenities']
    s = format_data(row, col_widths)
    print(s)  # to stdout
    txtfile.write(s) # to file
    txtfile.write("\n")

    for elem in desc:
        interior_features, space_amenities = features(elem)
        if interior_features or space_amenities: # only write elements with features
            row = ["property in somewhere", interior_features, space_amenities]
            s = format_data(row, col_widths)
            print(s)  # to stdout
            txtfile.write(s) # to file
            txtfile.write("\n")

输出

property in somewhere   interior_features                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   space_amenities                       
property in somewhere   Appliances included: Dishwasher, Dryer, Microwave, Range / Oven, Refrigerator, Washer, Appliances that stay: Range/Oven, Dishwasher, Refrigerator, Washer, Dryer, Master bedroom location: Main, Dining room location: Main, Heating and cooling: 90%+ High Efficiency, Forced Air, Features: Dbl Pane/Storm Windw, Dining Room, Security System, Ceiling Fan(s), Hot Tub/Spa, Heating: Gas, Floor size: 2,070 sqft, Utility room location: Lower, Living room location: Main, Addition size: 900, Beds: 3, Basement: Partially Finished, Flooring: Carpet, Hardwood, Tile, None: Ceiling Fan, Floor covering: Hardwood, Laminate, Wall to Wall Carpet, Kitchen location: Main                                            
property in somewhere                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       None: Security System, Unit count: 1  

【讨论】:

  • 您确实误解了我所期望的输出。查看 csv 输出的编辑。我从来没有说过我解析字段的方式是这样做的理想方式。鉴于如果出现更好的逻辑,总是可以纠正解析逻辑以去除那些制表符和空格。谢谢。
  • @robots.txt--感谢您的澄清。我相应地修改了我的答案。
  • @robots.txt——误解是你把它称为 CSV 文件,它通常不需要对齐文本来显示(例如,可以使用选项卡来识别每个字段) .我在字段之间放置了一个选项卡,因此尽管有所有额外的空间使其列对齐,但它仍然可以作为 CSV 处理。
最近更新 更多