在 C# 中管理复杂的字符串数组
Manage complex string array in C#
我想使用存储在 web.config
中的字符串数组来轻松更改其值,格式为:full_w=670|small_w=100,q=low|tiny_h=30,c=true
。每个模板由 | 分割(管道),然后这些集合中的每一个都包含一个名称(_ 的左侧)及其相应的值(_ 的右侧),这些值可以是多个,每个值由 ,(逗号)分隔。我认为这可能符合 3D 阵列的条件,我似乎无法找到一种简单的方法来以明智的方式阅读它。关于从该字符串中 read/manage 数据的最佳方式的任何想法或解决方案?
基本上,最后我希望能够调用模板 small
并读取其值,在本例中为 width=100
和 quality=low
。
这是我为解析这些设置字符串之一而编写的函数:
public static Dictionary<string, Dictionary<string, string>> getSettings(string settingsStr)
{
return settingsStr.Split('|').ToDictionary(
template => template.Split('_')[0],
template => template.Split('_')[1].Split(',').ToDictionary(
setting => setting.Split('=')[0],
setting => setting.Split('=')[1]));
}
它只是使用了很多字符串 .Split
ting 和 .ToDictionary
ing。
这是测试,表明它有效:
var result = getSettings("full_w=670|small_w=100,q=low|tiny_h=30,c=true");
/*
result = {
[ "full" => [ "w" => "670" ] ]
[ "small" => [ "w" => "100", "q" => "low" ] ]
[ "tiny" => [ "h" => "30", "c" => "true" ] ]
}
*/
要从模板 small
中读取值 w
和 q
,您可以这样做:
int width = int.Parse(result["small"]["w"]);
string quality = result["small"]["q"];
编辑: 作为额外的好处,如果您想将 Dictionary<string, Dictionary<string, string>>
转换回单个设置字符串,您可以使用此方法:
public static string getSettingsStr(Dictionary<string, Dictionary<string, string>> settings)
{
return string.Join("|",
settings.Select(kvp =>
kvp.Key + "_" + string.Join(",",
kvp.Value.Select(setting =>
setting.Key + "=" + setting.Value))));
}
使用:
string settingsStr = getSettingsStr(result);
// settingsStr = "full_w=670|small_w=100,q=low|tiny_h=30,c=true"
如果要检查特定模板或设置是否存在,请使用 .ContainsKey()
方法:
// If I have "Dictionary<string, Dictionary<string, string>> settings;"
int width = -1;
string quality = null;
if (settings.ContainsKey("small"))
{
if (settings["small"].ContainsKey("w"))
width = int.Parse(settings["small"]["w"]);
if (settings["small"].ContainsKey("q"))
quality = settings["small"]["q"];
}
您是否考虑过对您自己的普通旧 C# 对象使用普通旧 XML 序列化。这是一个例子:
public class Program
{
static void Main(string[] args)
{
var data = new MyConfig[2];
for (int i = 0; i < 2; i++)
{
data[i] = new MyConfig { Name = "Name" + i };
data[i].Properties = new MyConfigAttribute[]
{
new MyConfigAttribute { Name = "Property Name " + i, Value = "Property Value " + i },
new MyConfigAttribute { Name = "2nd Property Name " + i, Value = "2nd Property Value " + i },
};
}
var serializer = new XmlSerializer(typeof(MyConfig[]));
using (StreamWriter tw = File.CreateText(@"c:\temp\myconfig.xml"))
{
serializer.Serialize(tw, data);
}
using (StreamReader tw = File.OpenText(@"c:\temp\myconfig.xml"))
{
var readBack = serializer.Deserialize(tw);
}
Console.ReadLine();
}
[XmlRoot("MY_CONFIG")]
public class MyConfig
{
[XmlElement("NAME")]
public string Name { get; set; }
[XmlArray]
[XmlArrayItem(typeof(MyConfigAttribute))]
public MyConfigAttribute[] Properties { get; set; }
}
[XmlRoot("MY_CONFIG_ATTRIBUTE")]
public class MyConfigAttribute
{
[XmlElement("ATTRIBUTE_NAME")]
public string Name { get; set; }
[XmlElement("ATTRIBUTE_VALUE")]
public string Value { get; set; }
}
}
基本上,您创建一个 class 来存储您的个人属性(在本例中为 MyConfigAttribute),将其包装在另一个 class 中以提供一组相关属性的名称(在本例中为 MyConfig例),然后使用正常的 XML 序列化将设置写到单独的 XML 文件中,就像这部分代码
var serializer = new XmlSerializer(typeof(MyConfig[]));
using (StreamWriter tw = File.CreateText(@"c:\temp\myconfig.xml"))
{
serializer.Serialize(tw, data);
}
您可以使用这段代码再次将其读回对象:
using (StreamReader tw = File.OpenText(@"c:\temp\myconfig.xml"))
{
var readBack = serializer.Deserialize(tw);
}
这样做的好处是:
- 易于理解和使用
- 您可以向自定义 class 添加功能,例如将值添加到属性数组,从而有助于将自定义屏幕包裹在它周围。
在 Google!
上查找 C# XML 序列化
我想使用存储在 web.config
中的字符串数组来轻松更改其值,格式为:full_w=670|small_w=100,q=low|tiny_h=30,c=true
。每个模板由 | 分割(管道),然后这些集合中的每一个都包含一个名称(_ 的左侧)及其相应的值(_ 的右侧),这些值可以是多个,每个值由 ,(逗号)分隔。我认为这可能符合 3D 阵列的条件,我似乎无法找到一种简单的方法来以明智的方式阅读它。关于从该字符串中 read/manage 数据的最佳方式的任何想法或解决方案?
基本上,最后我希望能够调用模板 small
并读取其值,在本例中为 width=100
和 quality=low
。
这是我为解析这些设置字符串之一而编写的函数:
public static Dictionary<string, Dictionary<string, string>> getSettings(string settingsStr)
{
return settingsStr.Split('|').ToDictionary(
template => template.Split('_')[0],
template => template.Split('_')[1].Split(',').ToDictionary(
setting => setting.Split('=')[0],
setting => setting.Split('=')[1]));
}
它只是使用了很多字符串 .Split
ting 和 .ToDictionary
ing。
这是测试,表明它有效:
var result = getSettings("full_w=670|small_w=100,q=low|tiny_h=30,c=true");
/*
result = {
[ "full" => [ "w" => "670" ] ]
[ "small" => [ "w" => "100", "q" => "low" ] ]
[ "tiny" => [ "h" => "30", "c" => "true" ] ]
}
*/
要从模板 small
中读取值 w
和 q
,您可以这样做:
int width = int.Parse(result["small"]["w"]);
string quality = result["small"]["q"];
编辑: 作为额外的好处,如果您想将 Dictionary<string, Dictionary<string, string>>
转换回单个设置字符串,您可以使用此方法:
public static string getSettingsStr(Dictionary<string, Dictionary<string, string>> settings)
{
return string.Join("|",
settings.Select(kvp =>
kvp.Key + "_" + string.Join(",",
kvp.Value.Select(setting =>
setting.Key + "=" + setting.Value))));
}
使用:
string settingsStr = getSettingsStr(result);
// settingsStr = "full_w=670|small_w=100,q=low|tiny_h=30,c=true"
如果要检查特定模板或设置是否存在,请使用 .ContainsKey()
方法:
// If I have "Dictionary<string, Dictionary<string, string>> settings;"
int width = -1;
string quality = null;
if (settings.ContainsKey("small"))
{
if (settings["small"].ContainsKey("w"))
width = int.Parse(settings["small"]["w"]);
if (settings["small"].ContainsKey("q"))
quality = settings["small"]["q"];
}
您是否考虑过对您自己的普通旧 C# 对象使用普通旧 XML 序列化。这是一个例子:
public class Program
{
static void Main(string[] args)
{
var data = new MyConfig[2];
for (int i = 0; i < 2; i++)
{
data[i] = new MyConfig { Name = "Name" + i };
data[i].Properties = new MyConfigAttribute[]
{
new MyConfigAttribute { Name = "Property Name " + i, Value = "Property Value " + i },
new MyConfigAttribute { Name = "2nd Property Name " + i, Value = "2nd Property Value " + i },
};
}
var serializer = new XmlSerializer(typeof(MyConfig[]));
using (StreamWriter tw = File.CreateText(@"c:\temp\myconfig.xml"))
{
serializer.Serialize(tw, data);
}
using (StreamReader tw = File.OpenText(@"c:\temp\myconfig.xml"))
{
var readBack = serializer.Deserialize(tw);
}
Console.ReadLine();
}
[XmlRoot("MY_CONFIG")]
public class MyConfig
{
[XmlElement("NAME")]
public string Name { get; set; }
[XmlArray]
[XmlArrayItem(typeof(MyConfigAttribute))]
public MyConfigAttribute[] Properties { get; set; }
}
[XmlRoot("MY_CONFIG_ATTRIBUTE")]
public class MyConfigAttribute
{
[XmlElement("ATTRIBUTE_NAME")]
public string Name { get; set; }
[XmlElement("ATTRIBUTE_VALUE")]
public string Value { get; set; }
}
}
基本上,您创建一个 class 来存储您的个人属性(在本例中为 MyConfigAttribute),将其包装在另一个 class 中以提供一组相关属性的名称(在本例中为 MyConfig例),然后使用正常的 XML 序列化将设置写到单独的 XML 文件中,就像这部分代码
var serializer = new XmlSerializer(typeof(MyConfig[]));
using (StreamWriter tw = File.CreateText(@"c:\temp\myconfig.xml"))
{
serializer.Serialize(tw, data);
}
您可以使用这段代码再次将其读回对象:
using (StreamReader tw = File.OpenText(@"c:\temp\myconfig.xml"))
{
var readBack = serializer.Deserialize(tw);
}
这样做的好处是:
- 易于理解和使用
- 您可以向自定义 class 添加功能,例如将值添加到属性数组,从而有助于将自定义屏幕包裹在它周围。
在 Google!
上查找 C# XML 序列化