C# 在字符串中查找值
我有一个有几行字符串的文件。每行表示键值的集合,例如:C# 在字符串中查找值,c#,.net,.net-3.5,C#,.net,.net 3.5,我有一个有几行字符串的文件。每行表示键值的集合,例如: Name=JUI;Type=HomeUser;Address=Belgium;Address=Liege;Address=Street Name=Tim;Type=HomeUser;Address=Belgium;Address=Hasselt;Address=Street Name=Kim;Type=Proff;Address=Germany;Address=Dusseldorf;Address=Street Name=Ils;Type=
Name=JUI;Type=HomeUser;Address=Belgium;Address=Liege;Address=Street
Name=Tim;Type=HomeUser;Address=Belgium;Address=Hasselt;Address=Street
Name=Kim;Type=Proff;Address=Germany;Address=Dusseldorf;Address=Street
Name=Ils;Type=Proff;Address=Germany;Address=Munich;Address=Street
Name=Jan;Type=Student;Address=Germany;Address=Frankfurt;Address=Street
Name=Dav;Type=Student;Address=France;Address=Mitz;Address=Street
Name=Soli;Type=HomeUser;Address=France;Address=Lyon;Address=Street
Name=Mik;Type=HomeUser;Address=Switzerland;Address=Zurich;Address=Street
Name=Peter;Type=Blocked;Address=Netherland;Address=Enschede;Address=Street
Name=Maz;Type=Blocked;Address=Germany;Address=Achen;Address=Street
Name=Jo;Type=Teacher;Address=Belgium;Address=Antwerpen;Address=Street
我怎样才能做到以下几点:
有一种简单的方法可以做到这一点吗?我认为可以使用正则表达式将标记与反向引用相匹配
看看这个。我认为可以使用正则表达式将标记与反向引用匹配 看看这个。在所有这些情况下,当您有更好的数据表示时,答案非常简单-您可以使用LINQ 然而,第一步将是解析数据。对其进行如下建模:
public class User // ???
{
public string Name { get; private set; }
public string Type { get; private set; } // Should this be an enum?
public IList<string> Addresses { get; private set; }
// Could make this a constructor if you really want... I like the
// explicit nature of the static factory method.
public static User ParseLine(string line)
{
// TODO: Split line into components etc
}
}
string tNILF = myStruct.Where(element => element.Type == "HomeUser" /* || etc. */).Select(element => element.Name);
公共类用户//???
{
公共字符串名称{get;private set;}
公共字符串类型{get;private set;}//是否应为枚举?
公共IList地址{get;private set;}
//如果你真的想的话,可以把它变成构造函数…我喜欢
//静态工厂方法的显式性质。
公共静态用户解析行(字符串行)
{
//TODO:将线路拆分为组件等
}
}
如果你有一个列表
,你的查询将非常简单,但将“将数据放入更自然的表示”与“对数据进行有趣的操作”分开是很重要的
这是一个比这一特定示例更一般的观点,但始终尽可能早地将数据转换为自然、有用的表示形式,然后尽可能长时间地将其保存在该表示形式中。如果可能的话,只处理代码边界处的笨拙表示(通常是字符串)。在所有这些情况下,当您有更好的数据表示时,答案非常简单-您可以使用LINQ
然而,第一步将是解析数据。对其进行如下建模:
public class User // ???
{
public string Name { get; private set; }
public string Type { get; private set; } // Should this be an enum?
public IList<string> Addresses { get; private set; }
// Could make this a constructor if you really want... I like the
// explicit nature of the static factory method.
public static User ParseLine(string line)
{
// TODO: Split line into components etc
}
}
string tNILF = myStruct.Where(element => element.Type == "HomeUser" /* || etc. */).Select(element => element.Name);
公共类用户//???
{
公共字符串名称{get;private set;}
公共字符串类型{get;private set;}//是否应为枚举?
公共IList地址{get;private set;}
//如果你真的想的话,可以把它变成构造函数…我喜欢
//静态工厂方法的显式性质。
公共静态用户解析行(字符串行)
{
//TODO:将线路拆分为组件等
}
}
如果你有一个列表
,你的查询将非常简单,但将“将数据放入更自然的表示”与“对数据进行有趣的操作”分开是很重要的
这是一个比这一特定示例更一般的观点,但始终尽可能早地将数据转换为自然、有用的表示形式,然后尽可能长时间地将其保存在该表示形式中。如果可能的话,只处理代码边界处的笨拙表示(通常是字符串)。创建一个正则表达式来解析项:
“Name=(.+?);Type=(.+?);Address=(.+?)等”
然后您可以创建一个类来保存所有信息
class Record { public string Name; public string Type; public string Address; public string Address2; public string Address3}
然后将每一行与正则表达式匹配,填充匹配组中的字段,创建类的实例,并将它们添加到列表记录中
现在,您可以使用linq轻松搜索:
类型为HomeUser:records。其中(p=>p.type==“HomeUser”)
地址是德国:记录。其中(p=>p.Address==“德国”)
地址是里昂:记录。其中(p=>p.Address==“里昂”)
您可以轻松地扩展此示例,查看所有3个地址字段,创建一个正则表达式来解析项:“Name=(.+?);Type=(.+?);address=(.+?)等”
然后您可以创建一个类来保存所有信息
class Record { public string Name; public string Type; public string Address; public string Address2; public string Address3}
然后将每一行与正则表达式匹配,填充匹配组中的字段,创建类的实例,并将它们添加到列表记录中
现在,您可以使用linq轻松搜索:
类型为HomeUser:records。其中(p=>p.type==“HomeUser”)
地址是德国:记录。其中(p=>p.Address==“德国”)
地址是里昂:记录。其中(p=>p.Address==“里昂”)
您可以很容易地扩展此示例,查看所有3个地址字段首先定义一个结构会更容易
struct MyStruct
{
public string Name, Type /* etc.*/ ;
}
之后,您需要拆分输入
string[] arrayOfInputs = inpuString.Split(new char[]{Environment.NewLine, '\n', '\r'}) // splits your input, such that every element represents a line
List<MyStruct> myStruct = new List<MyStruct>;
foreach (string s in arrayOfInputs)
{
string[] arrayOfFields = s.Split(';');
// arrayOfFields[0] == "Name=name"
// arrayOfFields[1] == "Type=type"
// etc. extract needed info
myStruct.Add(new MyStruct(/* arguments go here */))
}
或者,您可以这样做:
public class User // ???
{
public string Name { get; private set; }
public string Type { get; private set; } // Should this be an enum?
public IList<string> Addresses { get; private set; }
// Could make this a constructor if you really want... I like the
// explicit nature of the static factory method.
public static User ParseLine(string line)
{
// TODO: Split line into components etc
}
}
string tNILF = myStruct.Where(element => element.Type == "HomeUser" /* || etc. */).Select(element => element.Name);
首先定义一个结构会更容易
struct MyStruct
{
public string Name, Type /* etc.*/ ;
}
之后,您需要拆分输入
string[] arrayOfInputs = inpuString.Split(new char[]{Environment.NewLine, '\n', '\r'}) // splits your input, such that every element represents a line
List<MyStruct> myStruct = new List<MyStruct>;
foreach (string s in arrayOfInputs)
{
string[] arrayOfFields = s.Split(';');
// arrayOfFields[0] == "Name=name"
// arrayOfFields[1] == "Type=type"
// etc. extract needed info
myStruct.Add(new MyStruct(/* arguments go here */))
}
或者,您可以这样做:
public class User // ???
{
public string Name { get; private set; }
public string Type { get; private set; } // Should this be an enum?
public IList<string> Addresses { get; private set; }
// Could make this a constructor if you really want... I like the
// explicit nature of the static factory method.
public static User ParseLine(string line)
{
// TODO: Split line into components etc
}
}
string tNILF = myStruct.Where(element => element.Type == "HomeUser" /* || etc. */).Select(element => element.Name);
一种方法是将键值对读入动态对象的集合中。完成此操作后,可以使用动态运行时使用LINQ查询动态对象:
要创建动态对象的集合,请执行以下操作:
var users = str.Split("\r\n".ToArray(), StringSplitOptions.RemoveEmptyEntries)
.Select(x => x.Split(';')
.Select(p => p.Split('='))
.ToLookup(s => s[0], s => s[1])
.ToDictionary(l => l.Key, l => (l.Count() > 1)
? (object)l.ToList() : (object)l.First())
.ToExpando());
请注意此扩展方法的使用:
public static dynamic ToExpando(this IDictionary<string, object> dict)
{
IDictionary<string, object> expando = new ExpandoObject();
foreach (var kv in dict)
expando[kv.Key] = kv.Value;
return expando;
}
2.获取Address=Germany的类型(注意:。Address
是一个列表
):
3.获取address=Lyon的名称:
var namesInLyon = users.Where(u => u.Address.Contains("Lyon"))
.Select(u => u.Name);
一种方法是将键值对读入动态对象的集合中。完成此操作后,可以使用动态运行时使用LINQ查询动态对象:
要创建动态对象的集合,请执行以下操作:
var users = str.Split("\r\n".ToArray(), StringSplitOptions.RemoveEmptyEntries)
.Select(x => x.Split(';')
.Select(p => p.Split('='))
.ToLookup(s => s[0], s => s[1])
.ToDictionary(l => l.Key, l => (l.Count() > 1)
? (object)l.ToList() : (object)l.First())
.ToExpando());
请注意此扩展方法的使用:
public static dynamic ToExpando(this IDictionary<string, object> dict)
{
IDictionary<string, object> expando = new ExpandoObject();
foreach (var kv in dict)
expando[kv.Key] = kv.Value;
return expando;
}
2.获取Address=Germany的类型(注意:。Address
是一个列表
):
3.获取address=Lyon的名称:
var namesInLyon = users.Where(u => u.Address.Contains("Lyon"))
.Select(u => u.Name);
这里需要的信息远不止一堆作业。这些是字符串、整数、枚举、类吗。。。?这些应该是类的属性吗?在不知道我们在看什么的情况下,绝对没有办法回答这个问题。这些数据是如何被拉进C#并加以利用的?很抱歉,请允许我更简洁地解释一下我的意思。我的意思是,可能有100种或更多不同的方法来解析文件中的数据。我的意思是,如果你想在你的具体案例中找到最好的方法,更多关于数据的信息,数据的去向,以及我在哪里