Форум: "Начинающим";
Текущий архив: 2010.08.27;
Скачать: [xml.tar.bz2];
ВнизВопрос про XML Найти похожие ветки
← →
vegarulez (2010-04-15 09:45) [0]Привет всем мастерам!
Вопрос состоит в следующем есть XML файл состоящий из большого количества секций.
Вида :
<?xml version="1.0" encoding="windows-1251"?>
<response>
<a id="1" name="Иванов" pr="инженер">
<prs id="S" wtime="40" z="7000"/>
</a>
<a id="2" name="Петров" pr="повар">
<prs id="S" wtime="35" z="4000"/>
</a>
...
и т.д.
</response>
для получения параметров из XML до этого использовал код вот такого вида:
var
objXMLDoc : IXMLDOMDocument;
Node : IXMLDOMElement;
List,ListPrinc : IXMLDOMNodeList;
s_xml:AnsiString;
s_err:String;
id,name,pr:String;
begin
objXMLDoc.async := False;
objXMLDoc.loadXML(trim(Data.Text));
s_xml:=objXMLDoc.text;
Node := objXMLDoc.DocumentElement;
if Node<>nil then
Try
id := Node.selectNodes("/response/a/@id").Item[0].Text;
name := Node.selectNodes("/response/a/@name").Item[0].Text;
...
s_err:="Разобран успешно.";
except on E:exception do
s_err:="Ошибка разбора. "+ E.Message;
End; //10
end;
Вопрос, когда одна запись в XML так можно сделать но как мне прочитать 2-ую и последующие записи, когда у них начальная ветка имеет одинаковое название - "a"?
← →
vegarulez (2010-04-15 10:24) [1]Сижу, пытаюсь... вроде - получается считывать... при
считывании через счётчик при подстановке счёчика в
Item[i].Text;
но тогда вопрос, а как я узнаю когда остановить счётчик i?
т.е. что записи уже закончились.
Как определить количество записией включений тэга <a>?
← →
Плохиш © (2010-04-15 10:44) [2]цикл и childNodes
← →
vegarulez (2010-04-15 10:53) [3]
for i:=0 to Node.childNodes.length-1 do
оно?
← →
Медвежонок Пятачок © (2010-04-15 10:56) [4]цикл по элементам IXMLDOMNodeList
← →
Медвежонок Пятачок © (2010-04-15 10:57) [5]оно?
нет не оно
← →
Медвежонок Пятачок © (2010-04-15 11:21) [6]Рисуем одну полезную библиотечную функцию
function GetXPathValue(iNode : IXMLDOMNode; const AXPath : string; AWholeNode : boolean) : OleVariant;
var vNode : IXMLDOMNode;
begin
Result := Unassigned;
vNode := iNode.selectSingleNode(AXPath);
if vNode <> nil then
if AWholeNode then Result := vNode.text else Result := vNode.nodeValue;
end;
на базе нее создаем производные
function GetXPathValueStr(iNode : IXMLDOMNode; const AXPath : string; AWholeNode : boolean) : string;
function GetXPathValueInt(iNode : IXMLDOMNode; const AXPath : string; AWholeNode : boolean) : integer;
function GetXPathValueDbl(iNode : IXMLDOMNode; const AXPath : string; AWholeNode : boolean) : Double;
И все. Навсегда забываем про чайлдов парентов и прочий навигационный подход.
Далее:
List := objXMLDoc.SelectNodes("/response/a");
if (List <> nil) and (List.Length > 0) then
for i := 0 to Pred(List.length) do
begin
name := GetXPathValueStr(List.items[i],"./@name",False);
id := GetXPathValueInt(List.items[i],"./@id",False);
end;
← →
vegarulez (2010-04-15 12:57) [7]Спасибо большое! Очень помогло!
← →
vegarulez (2010-04-15 14:27) [8]по мере продвижения впрёд появляются ещё вопросы...
вопрос таакой...
добрался до места где xml ветка имеет вот такую структуру
<a id="65" name="Зверев" pr="Слесарь">
<prs id="A" wtime="5" z="1000"/>
<prs id="S" wtime="10" z="1500"/>
<prs id="M" wtime="20" z="2000"/>
</a>
Вопрос - как можно выкусить ветку:
<prs id="A" wtime="5" z="1000"/>
<prs id="S" wtime="10" z="1500"/>
<prs id="M" wtime="20" z="2000"/>
в отдельную переменную для записи в текстовом виде в бд. Т.е. просто целиком этот кусок без разбора в текстовом виде? Т.е. кусочек из этой ветки.
← →
Медвежонок Пятачок © (2010-04-15 14:49) [9]Получить узел a, дальше
ShowMessage(a.xml)
будет вместе с содержимым самого "а", но оно никак не помешает добраться до вложенных узлов после загрузки сохраненного текста обратно в документ
← →
vegarulez (2010-04-15 14:55) [10]т.е. я пытаюсь это с делать в текущей ветке, в которой сечас производиться разбор, как посоветовал Медвежонок Пятачок © (15.04.10 11:21) [6], потом - выкусить эту информацию с тегами prs записать в бд, потом в следующей, опять начать разбор, потом информацию с тегами prs опять выкусить записать в бд и т.д, по всему xml документу.
Я так полагаю если в List содержится текущий элемент разбора проще всего тогда в каждый текущий разбор новой ветки брать оттуда этот набор prs тегов.
Подскажите как это сделать?
пытаюсь сделать вот так -
var
s:string;
j:integer;
ListPrs: IXMLDOMNodeList;
...
ListPrs := objXMLDoc.SelectNodes("/response/a/prs");
j:=ListPrs.length;
for j:=0 to ListPrs.length-1 do
s:=s+ListPrs.item[j].xml;
но в этом случае он дёргает все постепенно, а мне нужно только в текущей ветке которую в i момент времени разбираю с помощью Медвежонок Пятачок © (15.04.10 11:21) [6].
← →
Медвежонок Пятачок © (2010-04-15 15:20) [11]в таком случае текущий узел должен быть элементом списка полученным через
selectnodes("/response/a");
это будет полным списком всех узлов "а", которые есть дети респонса в первом поколении
← →
vegarulez (2010-04-15 15:32) [12]Сдеал вот так:
ListPrs:=List.item[i].childNodes;
for j:=0 to ListPrs.length-1 do
if ListPrs.item[j].nodeName="prs" then
s:=s+ListPrs.item[j].xml;
Прокомментируй плиз этот кусочек... так как руки пока ещё не совсем оттуда откуда надо растут... может что переделать, но вроде рабит - выдаёт что требуется...
← →
Медвежонок Пятачок © (2010-04-15 17:13) [13]а что надо получить-то в итоге?
← →
vegarulez (2010-04-16 09:00) [14]Ну нужно получить нужно строку, чтобы в базу записать, чтобы при надобности прочесть. Т.е. часть параметров нужно сразу прочесть и на основании их записать часть параметров виде xml строки в базу, чтобы потом при обращении к этой записи прочесть нужные параметры, записанные в xml формате. поэтому я парсю тем кодом который ты дал и внутри каждой ветки, выкусываю xml строку, кодом который привёл в [12], чтобы записать её (строку) в бд в том виде в котором она есть. воть...
посоветуй и прокементируй плз, у тя опыта побольше...
Страницы: 1 вся ветка
Форум: "Начинающим";
Текущий архив: 2010.08.27;
Скачать: [xml.tar.bz2];
Память: 0.48 MB
Время: 0.103 c