2009-12-05 76 views
31

我有这个字符串如何将字符串分割成一本字典

string sx="(colorIndex=3)(font.family=Helvetica)(font.bold=1)"; 

,并正与

string [] ss=sx.Split(new char[] { '(', ')' }, 
    StringSplitOptions.RemoveEmptyEntries); 

取而代之的是分裂的话,我怎么可能分裂的结果为Dictionary<string,string>?该 产生的字典应该是这样的:

Key   Value 
colorIndex 3 
font.family Helvetica 
font.bold 1 

回答

17

可能有更有效的方式,但是这应该工作:

string sx = "(colorIndex=3)(font.family=Helvicta)(font.bold=1)"; 

var items = sx.Split(new[] { '(', ')' }, StringSplitOptions.RemoveEmptyEntries) 
    .Select(s => s.Split(new[] { '=' })); 

Dictionary<string, string> dict = new Dictionary<string, string>(); 
foreach (var item in items) 
{ 
    dict.Add(item[0], item[1]); 
} 
53

它可以使用LINQ ToDictionary()扩展方法来完成:

string s1 = "(colorIndex=3)(font.family=Helvicta)(font.bold=1)"; 
string[] t = s1.Split(new[] { '(', ')' }, StringSplitOptions.RemoveEmptyEntries); 

Dictionary<string, string> dictionary = 
         t.ToDictionary(s => s.Split('=')[0], s => s.Split('=')[1]); 

编辑:同样的结果可以实现不分裂双胞胎E:

Dictionary<string, string> dictionary = 
      t.Select(item => item.Split('=')).ToDictionary(s => s[0], s => s[1]); 
+0

甚至不知道Split函数可以将字符串数组作为参数。整齐。 – 2009-12-05 14:47:31

+4

有没有办法避免调用's.Split()'两次? – 2009-12-05 15:14:55

+13

当然,通过调用t.Select(item => item.Split('='))。ToDictionary(s => s [0],s => s [1]);类似于@erikkallen&@Luke的答案。 – Elisha 2009-12-05 15:18:41

9
var dict = (from x in s1.Split(new[] { '(', ')' }, StringSplitOptions.RemoveEmptyEntries) 
      select new { s = x.Split('=') }).ToDictionary(x => x[0], x => x[1]); 
2

你可以用正则表达式做到这一点:

string sx = "(colorIndex=3)(font.family=Helvetica)(font.bold=1)"; 

Dictionary<string,string> dic = new Dictionary<string,string>(); 

Regex re = new Regex(@"\(([^=]+)=([^=]+)\)"); 

foreach(Match m in re.Matches(sx)) 
{ 
    dic.Add(m.Groups[1].Value, m.Groups[2].Value); 
} 

// extract values, to prove correctness of function 
foreach(var s in dic) 
    Console.WriteLine("{0}={1}", s.Key, s.Value); 
16

RandalSchwartzrule of thumb:采用分体式,当你知道你想扔掉什么或正则表达式时,你知道你想保留什么。

你知道你要保留什么:

string sx="(colorIndex=3)(font.family=Helvetica)(font.bold=1)"; 

Regex pattern = new Regex(@"\((?<name>.+?)=(?<value>.+?)\)"); 

var d = new Dictionary<string,string>(); 
foreach (Match m in pattern.Matches(sx)) 
    d.Add(m.Groups["name"].Value, m.Groups["value"].Value); 

随着一点点努力,你可以用ToDictionary做到这一点:

var d = Enumerable.ToDictionary(
    Enumerable.Cast<Match>(pattern.Matches(sx)), 
    m => m.Groups["name"].Value, 
    m => m.Groups["value"].Value); 

不知道这是否看起来更好:

var d = Enumerable.Cast<Match>(pattern.Matches(sx)). 
    ToDictionary(m => m.Groups["name"].Value, 
       m => m.Groups["value"].Value); 
+3

+1从来没有听说过这个规则,但我喜欢它! :) – 2009-12-05 14:03:28

13
string sx = "(colorIndex=3)(font.family=Helvetica)(font.bold=1)"; 

var dict = sx.Split(new[] { '(', ')' }, StringSplitOptions.RemoveEmptyEntries) 
      .Select(x => x.Split('=')) 
      .ToDictionary(x => x[0], y => y[1]); 
+0

嗯,我只注意到,这在功能上与erikkallen的答案相同,但使用扩展方法的语法而不是查询语法。 – LukeH 2009-12-05 14:18:13

+0

@Luke,对我来说,你的答案更具可读性,但可能只是格式化。 – 2009-12-05 14:34:24

+0

@Tuzo:我通常更喜欢扩展方法的语法,但我认为这完全取决于个人的品味。 – LukeH 2009-12-05 14:51:51

0

,我只是把这个在这里以供参考......

对于ASP.net,如果你想从客户端的字符串解析成一个字典,这是方便...

上创建一个JSON字符串在客户端或者是这样的:

var args = "{'A':'1','B':'2','C':'" + varForC + "'}"; 

或这样的:

var args = JSON.stringify(new { 'A':1, 'B':2, 'C':varForC}); 

甚至像这样:

var obj = {}; 
obj.A = 1; 
obj.B = 2; 
obj.C = varForC; 
var args = JSON.stringify(obj); 

将它传递给服务器...

然后分析它在服务器端是这样的:

JavaScriptSerializer jss = new JavaScriptSerializer(); 
Dictionary<String, String> dict = jss.Deserialize<Dictionary<String, String>>(args); 

JavaScriptSerializer需要System.Web.Script.Serialization。

3

您可以尝试

string sx = "(colorIndex=3)(font.family=Helvetica)(font.bold=1)"; 

var keyValuePairs = sx.Split(new[] { '(', ')' }, StringSplitOptions.RemoveEmptyEntries) 
      .Select(v => v.Split('=')) 
      .ToDictionary(v => v.First(), v => v.Last()); 
1

通常用于HTTP查询拆分。

Usage: Dictionary<string, string> dict = stringToDictionary("userid=abc&password=xyz&retain=false"); 

public static Dictionary<string, string> stringToDictionary(string line, char stringSplit = '&', char keyValueSplit = '=') 
{ 
    return line.Split(new[] { stringSplit }, StringSplitOptions.RemoveEmptyEntries).Select(s => s.Split(new[] { keyValueSplit })).ToDictionary(x => x[0], y => y[1]); ; 
}