2015-06-26 3 views
1

У меня есть XML, который выглядит, как этотВыбор определенных дочерних узлов в xml?

<SolutionString> 
    <Solutions> 
    <Solution> 
     <ID>1</ID> 
     <Property> 
     <Name>DriverSheave</Name> 
     <Value>1VP34</Value> 
     </Property> 
     <Property> 
     <Name>DriverBushing</Name> 
     <Value> 
     </Value> 
     </Property> 
     <Property> 
     <Name>DrivenSheave</Name> 
     <Value>AK49</Value> 
     </Property> 
     <Property> 
     <Name>DrivenBushing</Name> 
     <Value> 
     </Value> 
     </Property> 
     <Property> 
     <Name>Belt</Name> 
     <Value>AX30</Value> 
     </Property> 
     <Property> 
     <Name>BeltQty</Name> 
     <Value>1</Value> 
     </Property> 
     <Property> 
     <Name>ActualCenterDistance</Name> 
     <Value>9.88</Value> 
     </Property> 
    <Property> 
     <Name>ActualServiceFactor</Name> 
     <Value>1.71</Value> 
     </Property> 
    <Property> 
     <Name>ActualDrivenShaftSpeed</Name> 
     <Value>745/1117</Value> 
     </Property> 
    <Property> 
     <Name>Cost</Name> 
     <Value>32.65</Value> 
     </Property> 
     <TechSpecs> 
     <TurnsOpen>2.5/4.0</TurnsOpen> 
     <HubLoad>55 lb. 'running' Hub Load</HubLoad> 
     <Tension>1.93 lb. should deflect belt 0.15 in.</Tension> 
     </TechSpecs> 
     <Property> 
     <Name>Comment1</Name> 
     <Value>If Driver is 2.5 turns open Driven RPM=931 and CD=10.25 in. If Driver is 4.0 turns open Driven RPM=819 and CD=10.47 in.</Value> 
     </Property> 
     <Property> 
     <Name>Comment2</Name> 
     <Value>Correct tension for this drive (1.93 lb. should deflect belt 0.15 in.) will have 55 lb. 'running' Hub Load</Value> 
     </Property> 
     <Interchanges> 
     <Interchange> 
      <DriverSheave /> 
      <DriverBushing /> 
      <DrivenSheave>BK55X7/8</DrivenSheave> 
      <DrivenBushing> 
      </DrivenBushing> 
     </Interchange> 
     <Interchange> 
      <DriverSheave /> 
      <DriverBushing /> 
      <DrivenSheave>AK49H</DrivenSheave> 
      <DrivenBushing>H</DrivenBushing> 
     </Interchange> 
     <Interchange> 
      <DriverSheave /> 
      <DriverBushing /> 
      <DrivenSheave>BK55H</DrivenSheave> 
      <DrivenBushing>H</DrivenBushing> 
     </Interchange> 
     </Interchanges> 
    </Solution> 
    <Solution> 

Для значения списка свойств 2, он выбирает оба

<Property> 
    <Name>DrivenSheave</Name> 
    <Value>AK49</Value> 
    </Property> 

, а также

<Property> 
    <Name>Comment2</Name> 
    <Value>Correct tension for this drive (1.93 lb. should deflect belt 0.15 in.) will have 55 lb. 'running' Hub Load</Value> 
    </Property> 

я считаю его из-за разрыва в свойствах с <techspecs>

Im, используя такой код, чтобы загрузить каждый идентификатор и его свойства в комбинированный блок, подобный этому.

var cat = solutions 
    .Descendants("Solution") 
    .Select(x => new 
    { 
     ID = (string)x.Element("ID"), 
     Properties = x.Elements("Property").Select(p => new 
     { 
      Name = (string) p.Element("Name"), 
      Value = (string) p.Element("Value") 
     }).ToList() 
    }); 

var items = cat 
    .Select(s => new 
    { 
     ID = s.ID, 
     Text = string.Format("{0}. {1}", s.ID, 
     string.Join(", ", s.Properties 
          .Select(p => string.Format("{0} = {1}", 
           p.Name, 
           p.Value ?? "(null)")))) 
    }).ToArray(); 
comboBox1.DisplayMember = "Text"; 
comboBox1.ValueMember = "ID"; 
comboBox1.Items.AddRange(items); 

вопрос им нарваться, что для каждого Solution/ID есть 12 ребенок property «s. Я хотел бы быть в состоянии определить только 6 из них, так, например, выбирая первый

<Property> 
    <Name>DriverSheave</Name> 
    <Value>1VP34</Value> 
</Property> 

3-й один, 6-й один ЭСТ, и пропуская другие.

Ive посмотрите на это Select specific nodes in XML with LINQ, но я не уверен, как это реализовать в моей ситуации.

ответ

1

Вы можете сделать что-то вроде этого:

var indexesToChoose = new List<int> {1, 2}; 

var cat = solutions 
      .Descendants("Solution") 
      .Select(x => new 
      { 
       ID = (string)x.Element("ID"), 
       Properties = x.Elements("Property") 
        .Select((p, i) => new 
        { 
         Name = (string)p.Element("Name"), 
         Value = (string)p.Element("Value"), 
         idx = i 
        }) 
        .Where(y => indexesToChoose.Contains(y.idx)) 
        //.OrderBy(z => indexesToChoose.FindIndex(p => p == z.idx)) 
        .ToList() 
      }); 

Здесь первым мы создаем список индексов для выбора, то при создании каждого экземпляра анонимного класса мы перечисляем их, и, наконец, мы принимаем только те, у которых есть индексы в indexesToChoose.

В результате - после выполнения кода выше Properties поле будет содержать только первое и второеэлементы из xml.

+0

, это выглядит отлично, поэтому, если бы я хотел 2, 7, 10, я бы просто сделал 'var indexesToChoose = new List , {2, 7, 10 }; более того, я вижу, что Linq больше похож на SQL-заявление, и он просто пытается узнать форматирование ха-ха. –

+0

@AndrewKucenski да, точно. –

+0

, если я поставлю те, которые я хочу, так: '{7, 2, 10}' будет их упорядочивать, или это будет отдельный '.orderby'? –

1

Этот ответ поможет вам: Getting Nth value with Linq

var nthItem = items.Skip(n).First(); 
+0

Это похоже на то, что я хочу, но мое знание Linq неустойчиво, где бы я реализовал этот кусок кода? –

+0

im мой код это было бы, 'var nthitem = cat.skip (1) .First();'? –

+0

Да, это должно сделать трюк, как только вы выбрали решение, тогда вы хотите найти его n-го ребенка. Я бы предложил изменить имя переменной 'cat' на' solution' –