C#:XmlTextWriter.WriteElementString 在空字符串上失败?

发布于 2024-07-28 23:24:03 字数 879 浏览 0 评论 0原文

我正在使用 XmlTextWriter 及其 WriteElementString 方法,例如:

XmlTextWriter writer = new XmlTextWriter("filename.xml", null);

writer.WriteStartElement("User");
writer.WriteElementString("Username", inputUserName);
writer.WriteElementString("Email", inputEmail);
writer.WriteEndElement();

writer.Close();

预期的 XML 输出为:

<User>
    <Username>value</Username>
    <Email>value</Email>
</User>

但是,如果例如 inputEmail 为空,则我得到的结果 XML 如下:

<User>
    <Username>value</Username>
    <Email/>
</User>

而我希望它是:

<User>
    <Username>value</Username>
    <Email></Email>
</User>

我做错了什么? 有没有办法使用 XmlTextWriter 以简单的方式实现我的预期结果?

I'm using XmlTextWriter and its WriteElementString method, for example:

XmlTextWriter writer = new XmlTextWriter("filename.xml", null);

writer.WriteStartElement("User");
writer.WriteElementString("Username", inputUserName);
writer.WriteElementString("Email", inputEmail);
writer.WriteEndElement();

writer.Close();

The expected XML output is:

<User>
    <Username>value</Username>
    <Email>value</Email>
</User>

However, if for example inputEmail is empty, the result XML I get as as follows:

<User>
    <Username>value</Username>
    <Email/>
</User>

Whereas I would expect it to be:

<User>
    <Username>value</Username>
    <Email></Email>
</User>

What am I doing wrong? Is there a way to achieve my expected result in a simple way using XmlTextWriter?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

如果没有你 2024-08-04 23:24:03

你的输出是正确的。 没有内容的元素应该写成

您可以通过调用 WriteFullEndElement() 强制使用完整标记,

writer.WriteStartElement("Email");
writer.WriteString(inputEmail);
writer.WriteFullEndElement();

当 inputEmail 为空时,它将输出

如果您想多次执行此操作,您可以创建一个扩展方法:

public static void WriteFullElementString(this XmlTextWriter writer,
                                          string localName, 
                                          string value)
{
    writer.WriteStartElement(localName);
    writer.WriteString(value);
    writer.WriteFullEndElement();
}

然后您的代码将变为:

writer.WriteStartElement("User");
writer.WriteFullElementString("Username", inputUserName);
writer.WriteFullElementString("Email", inputEmail);
writer.WriteEndElement();

Your output is correct. An element with no content should be written as <tag/>.

You can force the use of the full tag by calling WriteFullEndElement()

writer.WriteStartElement("Email");
writer.WriteString(inputEmail);
writer.WriteFullEndElement();

That will output <Email></Email> when inputEmail is empty.

If you want to do that more than once, you could create an extension method:

public static void WriteFullElementString(this XmlTextWriter writer,
                                          string localName, 
                                          string value)
{
    writer.WriteStartElement(localName);
    writer.WriteString(value);
    writer.WriteFullEndElement();
}

Then your code would become:

writer.WriteStartElement("User");
writer.WriteFullElementString("Username", inputUserName);
writer.WriteFullElementString("Email", inputEmail);
writer.WriteEndElement();
纵性 2024-08-04 23:24:03

它不会失败只是的快捷方式

It doesn't fail <Tag/> is just a shortcut for <Tag></Tag>

如梦 2024-08-04 23:24:03

您的代码应该是:

using (XmlWriter writer = XmlWriter.Create("filename.xml"))
{
    writer.WriteStartElement("User");
    writer.WriteElementString("Username", inputUserName);
    writer.WriteElementString("Email", inputEmail);
    writer.WriteEndElement();
}

这可以避免出现异常时的资源泄漏,并使用正确的方法创建 XmlReader(自 .NET 2.0 起)。

Your code should be:

using (XmlWriter writer = XmlWriter.Create("filename.xml"))
{
    writer.WriteStartElement("User");
    writer.WriteElementString("Username", inputUserName);
    writer.WriteElementString("Email", inputEmail);
    writer.WriteEndElement();
}

This avoids resource leaks in case of exceptions, and uses the proper way to create an XmlReader (since .NET 2.0).

南风起 2024-08-04 23:24:03

把它留在这里以备不时之需; 因为上面的答案都没有为我解决这个问题,或者看起来有点矫枉过正。

FileStream fs = new FileStream("file.xml", FileMode.Create);

XmlWriterSettings settings = new XmlWriterSettings();
settings.Indent = true;

XmlWriter w = XmlWriter.Create(fs, settings);
w.WriteStartDocument();
w.WriteStartElement("tag1");
w.WriteStartElement("tag2");
w.WriteAttributeString("attr1", "val1");
w.WriteAttributeString("attr2", "val2");
w.WriteFullEndElement();
w.WriteEndElement();
w.WriteEndDocument();

w.Flush();
fs.Close();

诀窍是设置XmlWriterSettings.Indent = true并将其添加到XmlWriter

编辑:

或者,您也可以使用

w.Formatting = Formatting.Indented;

XmlWriterSettings来代替添加。

Leaving this here in case someone needs it; since none of the answers above solved it for me, or seemed like overkill.

FileStream fs = new FileStream("file.xml", FileMode.Create);

XmlWriterSettings settings = new XmlWriterSettings();
settings.Indent = true;

XmlWriter w = XmlWriter.Create(fs, settings);
w.WriteStartDocument();
w.WriteStartElement("tag1");
w.WriteStartElement("tag2");
w.WriteAttributeString("attr1", "val1");
w.WriteAttributeString("attr2", "val2");
w.WriteFullEndElement();
w.WriteEndElement();
w.WriteEndDocument();

w.Flush();
fs.Close();

The trick was to set the XmlWriterSettings.Indent = true and add it to the XmlWriter.

Edit:

Alternatively you can also use

w.Formatting = Formatting.Indented;

instead of adding an XmlWriterSettings.

瑾夏年华 2024-08-04 23:24:03

尝试用另一种方法解决这个问题,可能需要优化。

public class SerializeConfig<T> where T : class
{
        public static string Serialize(T type)
        {
            var settings = new XmlWriterSettings
            {
                Encoding = Encoding.UTF8,
                Indent = true,
                OmitXmlDeclaration = true
            };
            var sb = new StringBuilder();
            var serializer = new XmlSerializer(type.GetType());
            using (var writer = XmlWriter.Create(sb, settings))
            {
                serializer.Serialize(writer, type);
            }

            return sb.ToString().FixXmlClosingTags();
        }
}
internal static class InsertStringExtention
{
    public static string FixXmlClosingTags(this string xmlString)
    {
        var sb = new StringBuilder();
        var xmlTags = xmlString.Split('\r');
        foreach (var tag in xmlTags)
        {
            if (tag.Contains("/>"))
            {
                var tagValue = tag.Replace("<", "").Replace("/>", "").Trim();
                var firstPart = tag.Substring(0, tag.IndexOf('<'));
                var newTag = $"{firstPart}<{tagValue}></{tagValue}>";
                sb.Append(newTag);
            }
            else
            {
                sb.Append(tag);
            }
            
        }
        return sb.ToString();
    }
}

Tried solving this with another approach, might need optimization.

public class SerializeConfig<T> where T : class
{
        public static string Serialize(T type)
        {
            var settings = new XmlWriterSettings
            {
                Encoding = Encoding.UTF8,
                Indent = true,
                OmitXmlDeclaration = true
            };
            var sb = new StringBuilder();
            var serializer = new XmlSerializer(type.GetType());
            using (var writer = XmlWriter.Create(sb, settings))
            {
                serializer.Serialize(writer, type);
            }

            return sb.ToString().FixXmlClosingTags();
        }
}
internal static class InsertStringExtention
{
    public static string FixXmlClosingTags(this string xmlString)
    {
        var sb = new StringBuilder();
        var xmlTags = xmlString.Split('\r');
        foreach (var tag in xmlTags)
        {
            if (tag.Contains("/>"))
            {
                var tagValue = tag.Replace("<", "").Replace("/>", "").Trim();
                var firstPart = tag.Substring(0, tag.IndexOf('<'));
                var newTag = 
quot;{firstPart}<{tagValue}></{tagValue}>";
                sb.Append(newTag);
            }
            else
            {
                sb.Append(tag);
            }
            
        }
        return sb.ToString();
    }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文