使用文件

时间:2015-11-05 16:50:57

标签: c# xml winforms xsd

我正在为个人项目构建XML编辑器。使用WinForms DataGridView控件和DataSet,我能够设置读取/编辑/保存,几乎没有问题,为每种类型使用单独的XML文件。

然而,当我开始尝试添加更多“高级”控件时,使用几个不同的文件变得很麻烦 - 需要if语句,具体取决于我使用的文件。所以,我尝试将这些文件合并到一个更大的文件中,如下所示:

<?xml version="1.0" encoding="utf-8" ?>
<Items>
  <Armor>
    <Item>
      <Name>Test Armor</Name>
      <Value>1234567</Value>
      <Rarity>Common</Rarity>
      <Slot>Chest</Slot>
      <Damage>1234567</Damage>
      <Defense>1234567</Defense>
      <Health>1234567</Health>
      <Mana>1234567</Mana>
      <Strength>1234567</Strength>
      <Dexterity>1234567</Dexterity>
      <FlavorText>Something about stuff</FlavorText>
      <ImageSource>C:\Items\img.gif</ImageSource>
    </Item>
  </Armor>
  <Consumables>
    <Item>
      <Name>Test Potion</Name>
      <Value>1234567</Value>
      <Damage>1234567</Damage>
      <Defense>1234567</Defense>
      <Health>0.1234567</Health>
      <Mana>0.1234567</Mana>
      <Strength>1234567</Strength>
      <Dexterity>1234567</Dexterity>
      <FlavorText>Something about stuff</FlavorText>
      <ImageSource>C:\Items\img.gif</ImageSource>
    </Item>
  </Consumables>
  <Junk>
    <Item>
      <Name>Test Junk</Name>
      <Value>1234567</Value>
      <Stackable>Yes</Stackable>
      <FlavorText>Something about stuff</FlavorText>
      <ImageSource>C:\Items\img.gif</ImageSource>
    </Item>
  </Junk>
  <QuestItems>
    <Item>
      <Name>Test Quest Item</Name>
      <Stackable>Yes</Stackable>
      <FlavorText>Something about stuff</FlavorText>
      <ImageSource>C:\Items\img.gif</ImageSource>
    </Item>
  </QuestItems>
  <Weapons>
    <Item>
      <Name>Test Weapon</Name>
      <Value>1234567</Value>
      <Rarity>Common</Rarity>
      <Slot>Primary</Slot>
      <Damage>1234567</Damage>
      <Defense>1234567</Defense>
      <Health>1234567</Health>
      <Mana>1234567</Mana>
      <Strength>1234567</Strength>
      <Dexterity>1234567</Dexterity>
      <FlavorText>Something about stuff</FlavorText>
      <ImageSource>C:\Items\img.gif</ImageSource>
    </Item>    
  </Weapons>
</Items>

从Visual Studio的Create Schema菜单生成并最低限度修改的架构,例如将unsignedInt更改为int

<?xml version="1.0" encoding="utf-8"?>
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <xs:element name="Items">
    <xs:complexType>
      <xs:sequence>
        <xs:element name="Armor">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="Item" maxOccurs="unbounded">
                <xs:complexType>
                  <xs:sequence>
                    <xs:element name="Name" type="xs:string" />
                    <xs:element name="Value" type="xs:int" />
                    <xs:element name="Rarity" type="xs:string" />
                    <xs:element name="Slot" type="xs:string" />
                    <xs:element name="Damage" type="xs:int" />
                    <xs:element name="Defense" type="xs:int" />
                    <xs:element name="Health" type="xs:int" />
                    <xs:element name="Mana" type="xs:int" />
                    <xs:element name="Strength" type="xs:int" />
                    <xs:element name="Dexterity" type="xs:int" />
                    <xs:element name="FlavorText" type="xs:string" />
                    <xs:element name="ImageSource" type="xs:string" />
                  </xs:sequence>
                </xs:complexType>
              </xs:element>
            </xs:sequence>
          </xs:complexType>
        </xs:element>
        <xs:element name="Consumables">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="Item" maxOccurs="unbounded">
                <xs:complexType>
                  <xs:sequence>
                    <xs:element name="Name" type="xs:string" />
                    <xs:element name="Value" type="xs:int" />
                    <xs:element name="Damage" type="xs:int" />
                    <xs:element name="Defense" type="xs:int" />
                    <xs:element name="Health" type="xs:decimal" />
                    <xs:element name="Mana" type="xs:decimal" />
                    <xs:element name="Strength" type="xs:int" />
                    <xs:element name="Dexterity" type="xs:int" />
                    <xs:element name="FlavorText" type="xs:string" />
                    <xs:element name="ImageSource" type="xs:string" />
                  </xs:sequence>
                </xs:complexType>
              </xs:element>
            </xs:sequence>
          </xs:complexType>
        </xs:element>
        <xs:element name="Junk">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="Item" maxOccurs="unbounded">
                <xs:complexType>
                  <xs:sequence>
                    <xs:element name="Name" type="xs:string" />
                    <xs:element name="Value" type="xs:int" />
                    <xs:element name="Stackable" type="xs:string" />
                    <xs:element name="FlavorText" type="xs:string" />
                    <xs:element name="ImageSource" type="xs:string" />
                  </xs:sequence>
                </xs:complexType>
              </xs:element>
            </xs:sequence>
          </xs:complexType>
        </xs:element>
        <xs:element name="QuestItems">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="Item" maxOccurs="unbounded">
                <xs:complexType>
                  <xs:sequence>
                    <xs:element name="Name" type="xs:string" />
                    <xs:element name="Stackable" type="xs:string" />
                    <xs:element name="FlavorText" type="xs:string" />
                    <xs:element name="ImageSource" type="xs:string" />
                  </xs:sequence>
                </xs:complexType>
              </xs:element>
            </xs:sequence>
          </xs:complexType>
        </xs:element>
        <xs:element name="Weapons">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="Item" maxOccurs="unbounded">
                <xs:complexType>
                  <xs:sequence>
                    <xs:element name="Name" type="xs:string" />
                    <xs:element name="Value" type="xs:int" />
                    <xs:element name="Rarity" type="xs:string" />
                    <xs:element name="Slot" type="xs:string" />
                    <xs:element name="Damage" type="xs:int" />
                    <xs:element name="Defense" type="xs:int" />
                    <xs:element name="Health" type="xs:int" />
                    <xs:element name="Mana" type="xs:int" />
                    <xs:element name="Strength" type="xs:int" />
                    <xs:element name="Dexterity" type="xs:int" />
                    <xs:element name="FlavorText" type="xs:string" />
                    <xs:element name="ImageSource" type="xs:string" />
                  </xs:sequence>
                </xs:complexType>
              </xs:element>
            </xs:sequence>
          </xs:complexType>
        </xs:element>
      </xs:sequence>
    </xs:complexType>
  </xs:element>
</xs:schema>

这两个文件完全代表其对应文件 - 我有ArmorConsumables等单独的文件。

预期结果是有一个文件代表以前单独的文件,例如:

Itemsroot节点。
Items内是父节点 - ArmorConsumables等 在每个父节点中是子节点Item及其属性。

据我所知,XML结构和架构看起来是正确的,但当我尝试将此文件读入我的程序时,收到错误:System.FormatException - "Input string was not in a correct format."

堆栈跟踪显示System.Number.StringToNumber正在抛出此异常。我已经挖掘了几次文件和模式,似乎无法找到发生的位置,并且异常细节没有提供更多详细信息。

在我的代码中,我只是使用

读取数据
DataSet data = new DataSet();            

data.ReadXmlSchema(itemSchema);
data.ReadXml(itemData);

当文件/架构是分开的时,这个确切的方法没有问题,这进一步让我相信我只是忽略了XML / Schema中的某些东西。

此时,我被困住了,不知道它可能是什么。如果有人能帮助我解决这个问题,我将不胜感激。

1 个答案:

答案 0 :(得分:1)

问题是您在每个项目类型上重复元素Item。 当您的代码读取架构时,它会找到Item元素的第一个外观,并尝试将相同的架构应用于其他每个外观;所以,当它读取Test Potion时会尝试将其读作stringintstringstringint,{{1 }},intintintintintstring并在找到0.1234567 string时失败值。

我的建议是将您的架构更改为以下内容:

Health