Форум сайта python.su
0
Здравствуйте уважаемые участники форума, пытаюсь разобраться с парсингом csv файлов. У меня есть файл в котором представлено множество колонок, из него необходимо выбрать несколько (номера известны) с их параметрами. Cложность заключается в том, что каждую из колонок необходимо переименовать.
Посоветуйте пожалуйста рабочую модель, чтобы было от чего отталкиваться. Спасибо.
Офлайн
0
Поискал по форуму везде обсуждается парсинг XML, а мне нужно все с точностью наоборот. Необходимо произвести парсинг CSV с выгрузкой в XML. На просторах интернета я нашел прекрасный скрипт который работает несколько иначе, чем необходимо мне.
Спрашиваю в данной ветке, так как надеюсь, что мне помогут разобраться, дать некоторые комментарии.
Насколько я смог разобраться сам, данный скрипт меняет название колонок на тэги в xml, работая по диапазону. Хочется понять можно ли переделать этот код, чтобы искал только по выбранным полям и выгружал переименованные тэги в xml.
import csv csvFile = 'myData.csv' xmlFile = 'myData.xml' csvData = csv.reader(open(csvFile)) xmlData = open(xmlFile, 'w') xmlData.write('<?xml version="1.0"?>' + "\n") # there must be only one top-level tag xmlData.write('<csv_data>' + "\n") rowNum = 0 for row in csvData: if rowNum == 0: tags = row # replace spaces w/ underscores in tag names for i in range(len(tags)): tags[i] = tags[i].replace(' ', '_') else: xmlData.write('<row>' + "\n") for i in range(len(tags)): xmlData.write(' ' + '<' + tags[i] + '>' \ + row[i] + '</' + tags[i] + '>' + "\n") xmlData.write('</row>' + "\n") rowNum +=1 xmlData.write('</csv_data>' + "\n") xmlData.close()
Офлайн
857
Приведи пример входного файла и выходного файла, который должен из него получиться.
Офлайн
0
Входной файл содержит структуру:
nazvanie-oblast-opisanie-total
ob'ekt1-15-Opisanie-20
На выходе должен получится xml:
<row>
<title>ob'ekt1</title>
<area>15</area>
<description>Opisanie</opisanie>
<total>20</total>
</row>
Где колонка “nazvanie” приобретает тэг <title>
Колонка “oblast” приобретает тэг <area>
Колонка “opisanie” приобретает тэг <description>
А “total” остается неизменной.
С переименованием я кстати разобрался. Не знаю насколько это корректно с точки зрения профессионалов, но у меня получилось несколько строк:
tags[i] = tags[i].replace(' ', '_')
tags[i] = tags[i].replace('nazvanie', 'title') tags[i] = tags[i].replace('oblast', 'area') tags[i] = tags[i].replace('opisanie', 'description')
Офлайн
857
Напиши входную строку со всеми полями и выходной xml с выбранными из неё полями.
i.zЭто не входной файл, а просто выбранные поля из входного файла. А входной файл так и остался неизвестным.
Входной файл содержит структуру:
i.zВот, теперь ты поля строками называешь.
Теперь ищу ответ на вопрос “Как вывести в xml только те строки, которые мне необходимы”
i.z.replace() там вообще нигде не должно быть.
Не знаю насколько это корректно с точки зрения профессионалов
Отредактировано py.user.next (Окт. 22, 2015 11:10:03)
Офлайн
0
py.user.nextПрошу прощения, добавляю файл с которым работаю.
Это не входной файл, а просто выбранные поля из входного файла. А входной файл так и остался неизвестным.
Предлагаешь нам догадаться, какой у тебя там входной файл.
Прикреплённый файлы:
zemla.csv (92,7 KБ)
Офлайн
857
Вот две строки
>>> s1 '13,13,"Земельный участок в д.Курово г/п Дмитров",zemelnyj-uchastok-v-dkurovo-gp-dmitrov,da,tatyana,images/logo/d-kurovo/d-kurovo-logo.png,item-photo/d-kurovo,"д. Курово, Дмитровский район, Московская область, Россия",uchastki,"<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Продается земельный участок под застройку индивидуального жилого дома. Участок 8 соток в д.Курово г/п Дмитров.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Категория земель: земли населенных пунктов.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Разрешенное использование: для ведения личного подсобного хозяйства.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">После строительства дома, возможность прописаться (зарегистрироваться) по месту. Свет, газ на участке.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Кадастровый номер участка 50:04:0150401:353. Курортное место Подмосковья.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">У деревни находится популярный горнолыжный курорт ""Сорочаны"".Участок граничит с отелем ""Свежий Ветер"". Идеальное расположение в экологически чистом месте, центре активного отдыха. Хорошая транспортная доступность.</span></p>",,,"д. Курово, Дмитровский район, Московская область, Россия",zemli-selskohozyajstvennogo-naznacheniya,digs,8,da,da,da,asfalt,"2 400 000 rub"\n' >>> s2 '14,14,"Недостроенный жилой дом на 15 сот. д.Рождествено",prodaetsya-nedostroennyj-zhiloj-dom-na-15-sot-drozhdestveno,da,tatyana,images/logo/d-shebanovo/d-shebanovo.png,item-photo/d-shebanovo,"деревня Шебаново, Московская область, Россия",uchastki,"<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Продается недостроенный кирпичный дом на земельном участке под ИЖС на 15 (по факту 20) сотках в д.Рождествено Габовское с/п Дмитровского района.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Недостроенный кирпичный дом размером 10х12 метров, построен 1 этаж из облицовочного кирпича (цвет слоновая кость и шоколад).</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">На участке имеется хоз.блок деревянно-щитовой 2,5 х 6 м.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Участок ровный спланированный, хороший подъезд. На участке по границе с соседом имеется пруд размером 10х5м.</span></p>\n\n<p style=""text-align: justify;""><span style=""font-family: terminal, monaco; font-size: 14pt;"">Имеется тех. условия на подключение электричества 15 кВт 3-х фазное. Газ по границе. Лес в 50 м от участка.</span></p>",,,"деревня Шебаново, Московская область, Россия",zemli-naselyonnyh-punktov,digs,15,da,da,net,grunt,"2 890 000 rub"\n' >>>
>>> c 'id,sku,name,alias,"Есть изображение? (#1)","Агент отвечающий за объект (#2)","Основное фото (#3)","Галлерея (#4)","Карта (#5)","Тип недвижимости (#6)","Property Details (#7)","Agent (#8)","Mark (#9)","Адрес (#10)","Категория земель (#11)","Разрешенное использование (#12)","Количество соток (#13)","Электричество (#14)","Газ (#15)","Водопровод (#16)","Дорога (#17)",price_value_1\n' >>>
Отредактировано py.user.next (Окт. 22, 2015 13:55:02)
Офлайн
0
По скрипту который опубликован в самом начале выбирается все подряд, и на выходе мы имеем вот такую структуру
<?xml version=“1.0”?>
<csv_data>
<sub>
<id>13</id>
<sku>13</sku>
<name>Земельный участок в д.Курово г/п Дмитров</name>
<alias>zemelnyj-uchastok-v-dkurovo-gp-dmitrov</alias>
<author>Super User</author>
<created>2015-09-30 00:00:00</created>
<category>Земельные участки|||zemelnye-uchastki</category>
<tags></tags>
<Есть_изображение?_(#1)>da</Есть_изображение?_(#1)>
<Агент_отвечающий_за_объект_(#2)>tatyana</Агент_отвечающий_за_объект_(#2)>
<Основное_фото_(#3)>images/logo/d-kurovo/d-kurovo-logo.png</Основное_фото_(#3)>
<Галлерея_(#4)>item-photo/d-kurovo</Галлерея_(#4)>
<Карта_(#5)>д. Курово, Дмитровский район, Московская область, Россия</Карта_(#5)>
<Тип_недвижимости_(#6)>uchastki</Тип_недвижимости_(#6)>
<Property_Details_(#7)><p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Продается земельный участок под застройку индивидуального жилого дома. Участок 8 соток в д.Курово г/п Дмитров.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Категория земель: земли населенных пунктов.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Разрешенное использование: для ведения личного подсобного хозяйства.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>После строительства дома, возможность прописаться (зарегистрироваться) по месту. Свет, газ на участке.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Кадастровый номер участка 50:04:0150401:353. Курортное место Подмосковья.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>У деревни находится популярный горнолыжный курорт “Сорочаны”.Участок граничит с отелем “Свежий Ветер”. Идеальное расположение в экологически чистом месте, центре активного отдыха. Хорошая транспортная доступность.</span></p></Property_Details_(#7)>
<Agent_(#8)></Agent_(#8)>
<Mark_(#9)></Mark_(#9)>
<Адрес_(#10)>д. Курово, Дмитровский район, Московская область, Россия</Адрес_(#10)>
<Категория_земель_(#11)>zemli-selskohozyajstvennogo-naznacheniya</Категория_земель_(#11)>
<Разрешенное_использование_(#12)>digs</Разрешенное_использование_(#12)>
<Количество_соток_(#13)>8</Количество_соток_(#13)>
<Электричество_(#14)>da</Электричество_(#14)>
<Газ_(#15)>da</Газ_(#15)>
<Водопровод_(#16)>da</Водопровод_(#16)>
<Дорога_(#17)>asfalt</Дорога_(#17)>
<price_value_1>2 400 000 rub</price_value_1>
<?xml version=“1.0”?>
<csv_data>
<sub>
<id>13</id>
<name>Земельный участок в д.Курово г/п Дмитров</name>
<Тип_недвижимости_(#6)>uchastki</Тип_недвижимости_(#6)>
<Property_Details_(#7)><p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Продается земельный участок под застройку индивидуального жилого дома. Участок 8 соток в д.Курово г/п Дмитров.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Категория земель: земли населенных пунктов.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Разрешенное использование: для ведения личного подсобного хозяйства.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>После строительства дома, возможность прописаться (зарегистрироваться) по месту. Свет, газ на участке.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>Кадастровый номер участка 50:04:0150401:353. Курортное место Подмосковья.</span></p>
<p style=“text-align: justify;”><span style=“font-family: terminal, monaco; font-size: 14pt;”>У деревни находится популярный горнолыжный курорт “Сорочаны”.Участок граничит с отелем “Свежий Ветер”. Идеальное расположение в экологически чистом месте, центре активного отдыха. Хорошая транспортная доступность.</span></p></Property_Details_(#7)>
<Разрешенное_использование_(#12)>digs</Разрешенное_использование_(#12)>
<Количество_соток_(#13)>8</Количество_соток_(#13)>
<Электричество_(#14)>da</Электричество_(#14)>
<Газ_(#15)>da</Газ_(#15)>
<Водопровод_(#16)>da</Водопровод_(#16)>
<Дорога_(#17)>asfalt</Дорога_(#17)>
<price_value_1>2 400 000 rub</price_value_1>
</sub>
<Количество_соток_(#13)>8</Количество_соток_(#13)>
<area>8</area>.
<Property_Details_(#7)></Property_Details_(#7)>
<price_value_1 valuta="rub">2 400 000</price_value_1>
Отредактировано i.z (Окт. 22, 2015 15:33:10)
Офлайн
857
#!/usr/bin/env python3 import csv import xml.etree.ElementTree as ET import lxml.html def read_csv(fname): with open(fname, encoding='utf-8', newline='') as f: f.readline() reader = csv.reader(f) for i in reader: yield i def convert_csv_to_xml(csvstream, csvnums, xmlroot, xmlnode, xmlnames): out = '<?xml version="1.0"?>' doc = ET.Element(xmlroot) for i in csvstream: selected = select_fields(i, csvnums) section = make_xml_section(xmlnode, xmlnames, selected) node_clean_html(section[3]) node_value_to_attr(section[10], 'valuta') doc.append(section) out += ET.tostring(doc, encoding='unicode') return out def select_fields(lst, numbers): out = [i for n, i in enumerate(lst, 1) if n in numbers] return out def make_xml_section(parent, names, lst): sub = ET.Element(parent) for name, value in zip(names, lst): e = ET.Element(name) e.text = str(value) sub.append(e) return sub def node_clean_html(node): if node.text: node.text = clean(node.text) def clean(s): doc = lxml.html.fromstring(s) return ''.join(doc.xpath(r'.//text()')) def node_value_to_attr(node, attr_name): pref, suff = node.text.rsplit(None, 1) node.set(attr_name, suff) node.text = pref def write_xml(fname, xmldata): with open(fname, 'w', encoding='utf-8') as fout: print(xmldata, file=fout) def main(): ifname = 'zemla.csv' csv_nums = [1, 3, 10, 11, 16, 17, 18, 19, 20, 21, 22] ofname = 'zemla.xml' xml_root = 'csv_data' xml_node = 'sub' xml_names = ['id', 'name', 'type', 'details', 'permit', 'number', 'electricity', 'gas', 'water', 'road', 'price'] csv_stream = read_csv(ifname) xmldata = convert_csv_to_xml( csv_stream, csv_nums, xml_root, xml_node, xml_names ) write_xml(ofname, xmldata) if __name__ == '__main__': main()
Отредактировано py.user.next (Окт. 25, 2015 01:14:10)
Офлайн
0
py.user.next - это просто филигранно, огромное спасибо. Буду сидеть разбираться, что и как работает.
Офлайн