用于存储的XML或INI文件?

时间:2014-02-03 09:29:08

标签: c# xml ini

存储在我的程序中使用的值列表的最佳方法是什么,并允许用户更改它们? XML文件或INI文件为什么?

如果您有更好的建议,欢迎您。

编辑:为了得到最合适的答案,这里有一些细节。但是,答案可以帮助其他用户,因为自定义详细信息仅作为注释编写。

我有一系列元素,每个元素都标有“true”或“false”值 在我的程序中,我只想使用列表中带有“true”值的元素。

我只能使用带有“True”元素的Enum,但我希望用户选择他想要的元素,将false更改为true,反之亦然。

但是,我不希望他在每次执行中选择所需的元素。这就是为什么我考虑使用一个可以根据用户优先权轻松改变的文件。

6 个答案:

答案 0 :(得分:3)

我建议使用.NET默认方式,这肯定是XML。

使用XML,您可以获得优于INI格式的优势:

  • 分层数据结构
  • 复杂数据类型易于存储(序列化)
  • 您只需使用xsd
  • 进行验证即可
  • XML是标准化的,面向未来的

答案 1 :(得分:3)

在我看来,有很多选择,但如果没有经验,你应该尽可能地保持它。

一种方法是使用您可以使用项目本身生成的设置。

只需在解决方案资源管理器中点击Add > New Item,即可将设置文件添加到项目中,然后选择Settings File

This是一篇有关向设置文件添加列表的有用文章。


在您的情况下,您还可以选择string设置。只需使用以下内容将整数值保存到string

Properties.Settings.Default.SettingX = string.Join(",", array);

使用以下方法阅读它们:

string[] list = Properties.Settings.Default.SettingX.Split(',');

答案 2 :(得分:2)

您应该使用app.config configuration个文件。

它使用XML来存储设置,但框架会为您处理大部分脏工作。

如果您需要在运行时从应用程序更改设置,请查看Settings files

答案 3 :(得分:2)

回答最佳问题可能是一笔巨大的交易。我认为这里有几个很好的解决方案是我的,希望它有所帮助。

实际上我在很多应用程序上工作,所有这些应用程序都需要由最终用户配置。 花了一段时间使用'xml'后,我改为使用“propertyName”=“value”的简单ini文件。

我写了一个简单的类来处理这类文件。用法很简单

Settings.ConfigProperties cfProps = new Settings.ConfigProperties("c:\\test.ini");
//if the file exists it will be read

//to update or insert new values
cfProps.UpdateValue("myNewProperty", "myValue");

//to get a stored value
String readValue = cfProps.ToString("myNewProperty");

//to permanently write changes to the ini file
cfProps.Save();

这是代码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
namespace Settings
{
    public class ConfigProperties
    {
        public class PropertyList<T> : List<ConfigProperty>
        {
            public ConfigProperty this[String propertyName]
            {
                get
                {
                    ConfigProperty ret = null;
                    foreach (ConfigProperty cp in this)
                    {
                        if (cp.Name == propertyName)
                        {
                            ret = cp;
                            break;
                        }
                    }
                    return ret;
                }
                set
                {
                    ConfigProperty ret = null;
                    foreach (ConfigProperty cp in this)
                    {
                        if (cp.Name == propertyName)
                        {
                            ret = cp;
                            break;
                        }
                    }
                    value = ret;
                }
            }
            public PropertyList()
                : base()
            {

            }

            public void Add(String Name, String Value)
            {
                ConfigProperty cp = new ConfigProperty();
                cp.Name = Name;
                cp.Value = Value;
                this.Add(cp);
            }
        }
        public class ConfigProperty
        {
            public String Name { get; set; }
            public String Value { get; set; }
            public ConfigProperty()
            {
                Name = "newPropertyName_" + DateTime.Now.Ticks.ToString();
                Value = "";
            }
            public ConfigProperty(String name, String value)
            {
                Name = name;
                Value = value;
            }
        }

        public String FileName { get; set; }
        public PropertyList<ConfigProperty> CFCollection { get; private set; }

        public ConfigProperties()
            : this(AppDomain.CurrentDomain.BaseDirectory + "config.ini")
        {
        }

        public ConfigProperties(String fileName)
        {
            CFCollection = new PropertyList<ConfigProperty>();
            FileName = fileName;
            if (fileName != null && File.Exists(fileName))
            {
                ReadFile();
            }
        }

        private void ReadFile()
        {
            if (File.Exists(FileName))
            {
                CFCollection = new PropertyList<ConfigProperty>();
                using (StreamReader sr = new StreamReader(FileName, Encoding.Default))
                {
                    while (!sr.EndOfStream)
                    {
                        String line = sr.ReadLine();
                        if (!line.StartsWith("#"))
                        {
                            ConfigProperty cf = new ConfigProperty();
                            String tmp = "";
                            Char splitter = '=';
                            for (int i = 0; i < line.Length; i++)
                            {
                                if (line[i] != splitter)
                                {
                                    tmp += ((Char)line[i]).ToString();
                                }
                                else
                                {
                                    cf.Name = tmp;
                                    tmp = "";
                                    splitter = '\n';
                                }
                            }
                            cf.Value = tmp;
                            if (cf.Name.Length > 0)
                            {
                                CFCollection.Add(cf);
                            }
                        }
                    }

                    sr.Close();
                }
            }
        }

        private void SaveConfigProperty(ConfigProperty prop)
        {
            List<String> output = new List<String>();
            if (File.Exists(FileName))
            {
                using (StreamReader sr = new StreamReader(FileName, Encoding.Default))
                {
                    while (!sr.EndOfStream)
                    {
                        String line = sr.ReadLine();
                        if (line.StartsWith(prop.Name + "="))
                        {
                            output.Add(prop.Name + "=" + prop.Value);
                        }
                        else
                        {
                            output.Add(line);
                        }
                    }
                    sr.Close();
                }
            }

            if (!output.Contains(prop.Name + "=" + prop.Value))
            {
                output.Add(prop.Name + "=" + prop.Value);
            }

            StreamWriter sw = new StreamWriter(FileName, false, Encoding.Default);

            foreach (String s in output)
            {
                sw.WriteLine(s);
            }
            sw.Close();
            sw.Dispose();
            GC.SuppressFinalize(sw);
            sw = null;

            output.Clear();
            output = null;

        }

        public void Save()
        {
            foreach (ConfigProperty cp in CFCollection)
            {
                SaveConfigProperty(cp);
            }
        }

        public void UpdateValue(String propertyName, String propertyValue)
        {
            try
            {
                IEnumerable<ConfigProperty> myProps = CFCollection.Where(cp => cp.Name.Equals(propertyName));
                if (myProps.Count() == 1)
                {
                    myProps.ElementAt(0).Value = propertyValue;
                }
                else if (myProps.Count() == 0)
                {
                    CFCollection.Add(new ConfigProperty(propertyName, propertyValue));
                }
                else
                {
                    throw new Exception("Can't find/set value for: " + propertyName);
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

        public String ToString(String propertyName)
        {
            try
            {
                return CFCollection.Where(cp => cp.Name.Equals(propertyName)).First().Value;
            }
            catch (Exception ex)
            {
                throw new Exception("Can't find/read value for: " +
                    propertyName, ex);
            }
        }

    }
}

答案 4 :(得分:1)

您可以使用简单的普通文件。

List<int> list保存到file.txt

System.IO.File.WriteAllLines("file.txt", list.Select(v => v.ToString()).ToArray());

装载:

List<int> loaded = System.IO.File.ReadAllLines("file.txt").Select(l => int.Parse(l)).ToList();

使用扩展方法设计更好的语法和正确的错误处理

UPD :我可以提出的通用扩展方法(无异常处理):

public static class MyExtensions
{
    public static void SaveToFile<T>(this List<T> list, string filename)
    {
        System.IO.File.WriteAllLines(filename, list.Select(v => v.ToString()).ToArray());
    }

    public static void FillFromFile<T>(this List<T> list, string filename, Func<string, T> parser)
    {
        foreach (var line in System.IO.File.ReadAllLines(filename))
        {
            T item = parser(line);

            list.Add(item);
        }
    }
}

使用它:

List<int> list = new List<int>() { 0, 1, 2 };

list.SaveToFile("numbers.txt");

List<int> loaded = new List<int>();

loaded.FillFromFile("numbers.txt", (l) => int.Parse(l));

答案 5 :(得分:1)

我想建议JSON格式

  • 可由人
  • 阅读/编辑
  • 它支持层次结构
  • 它不像XML那样复杂
  • 它可以像魅力一样使用(没有丑陋的ini解析)

格式化文件看起来像

  

{ “DevCommentVisibility”:27, “CommentVisibility”:1, “IssueStatusAfterCheckin”:4, “日志”:{ “调试”:假, “信息”:真, “警告”:真, “文件名”:” d:\ TEMP \ 2.登录 “},” 语言 “:” EN“}

public static string Serialize(T pSettings)
{
    return (new JavaScriptSerializer()).Serialize(pSettings);
}

public static T Load(string fileName)
{
    T t = new T();
    if (File.Exists(fileName))
        try
        {
            t = (new JavaScriptSerializer()).Deserialize<T>(File.ReadAllText(fileName));
            var s = t as SettingsFoo;
            if (s != null)
                s.FileName = fileName;
        }
        catch (Exception ex)
        {
            Trace.WriteLine(string.Format("failed to parse settings file {0}", fileName));
            Trace.WriteLine(ex.Message);
        }
    else
    {
        Trace.WriteLine(string.Format("failed load settings '{0}' absolute '{1}'", fileName, Path.GetFullPath(fileName)));
        Save(t);
    }
    return t;
}