[英]How to convert a multi-line delimited string to a List<class>
I have a string delimited with new line.我有一个用新行分隔的字符串。
I can split it to 4 different list items but I need also split the content of each string, where the items use the |
我可以将它拆分为 4 个不同的列表项,但我还需要拆分每个字符串的内容,其中项目使用
|
character as separator.字符作为分隔符。
The internal values use Tags like BR=
, KS=
.内部值使用诸如
BR=
、 KS=
之类的标签。 I want to use the value of these tags to generate new class objects.我想使用这些标签的值生成新的 class 对象。
The class is named BIRIM
; class 名为
BIRIM
; it has Property names corresponding to the Tags in the strings.它具有与字符串中的标签相对应的属性名称。
My String:我的字符串:
BR=PALET90|KS=90|IS=1
BR=PALET60|KS=60|IS=1
BR=EUROPALET|KS=55|IS=1
BR=EUROPALET66|KS=66|IS=1
BR=PALET|KS=75|IS=1
My Current Code:我当前的代码:
public class BIRIM {
public string BR {get;set;}
public int KS {get;set;}
public int IS {get;set;}
}
string birim = node2["BIRIMLER"]?.InnerText;
string[] birimlerim = birim.Split(
new[] { Environment.NewLine },
StringSplitOptions.None
);
Technically, you can Split
several times:从技术上讲,您可以
Split
多次:
using System.Linq;
...
string source =
@"BR=PALET90|KS=90|IS=1
BR=PALET60|KS=60|IS=1
BR=EUROPALET|KS=55|IS=1
BR=EUROPALET66|KS=66|IS=1
BR=PALET|KS=75|IS=1";
...
var myList = source
.Split(new char[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries)
.Select(line => line
.Split('|')
.Select(item => item.Split('='))
.ToDictionary(item => item[0].Trim(), item => item[1]))
.Select(dict => new BIRIM() {
BR = dict["BR"],
KS = int.Parse(dict["KS"]),
IS = int.Parse(dict["IS"])
})
.ToList();
However, I suggest implementing TryParse
method within BIRIM
class, let this class parse for itself when necessary:但是,我建议在
BIRIM
class 中实现TryParse
方法,让这个 class 在必要时自行解析:
using System.Text.RegularExpressions;
...
public class BIRIM {
...
public static bool TryParse(string source, out BIRIM result) {
result = null;
if (string.IsNullOrWhiteSpace(source))
return false;
string br = Regex.Match(source, @"BR\s*=\s*(\w+)").Groups[1].Value;
string KS = Regex.Match(source, @"KS\s*=\s*([0-9]+)").Groups[1].Value;
string IS = Regex.Match(source, @"IS\s*=\s*([0-9]+)").Groups[1].Value;
if (!string.IsNullOrEmpty(br) &&
int.TryParse(KS, out int aks) &&
int.TryParse(IS, out int ais)) {
result = new BIRIM() {
BR = br,
KS = aks,
IS = ais,
};
return true;
}
return false;
}
}
Then you can implement the loading as然后你可以将加载实现为
var myList = source
.Split(new char[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries)
.Select(line => BIRIM.TryParse(line, out var value) ? value : null)
.Where(value => value != null)
.ToList();
try this instead of Environment.NewLine:试试这个而不是 Environment.NewLine:
string[] birimlerim = birim.Split(new string[] { "\r\n" }, StringSplitOptions.None);
You have to split multiple times你必须拆分多次
One implementation could be the following, but please consider to split it in more functions, it will be more readable and you can parse converted value.一种实现可能如下,但请考虑将其拆分为更多功能,这样可读性更强,并且您可以解析转换后的值。
private static List<BIRIM> ParseBirim(string birimText)
{
var birims = new List<BIRIM>();
string[] birimlerim = birimText.Trim().Split(Environment.NewLine);
foreach (string birim in birimlerim)
{
string[] bki = birim.Split('|');
birims.Add(new BIRIM
{
BR = bki[0].Split('=')[1],
KS = Convert.ToInt32(bki[1].Split('=')[1]),
IS = Convert.ToInt32(bki[2].Split('=')[1]),
});
}
return birims;
}
Another option.另外一个选择。
Parse the whole multi-line content using Regex.Matches() (specifying RegexOptions.Multiline
), iterate the MatchCollection items to build new BIRIM
objects with the values extracted.使用Regex.Matches() (指定
RegexOptions.Multiline
)解析整个多行内容,迭代MatchCollection项以使用提取的值构建新的BIRIM
对象。
string pattern = @"^BR=(?<br>.*?)\|KS=(?<ks>.*?)\|IS=(?<is>.*?)$";
string innerText = node2["BIRIMLER"]?.InnerText;
var birims = Regex.Matches(innerText, pattern, RegexOptions.Multiline)
.OfType<Match>().Select(m =>
new BIRIM(
m.Groups["br"].Value,
int.Parse('0' + m.Groups["ks"].Value.Trim()),
int.Parse('0' + m.Groups["is"].Value.Trim())))
.ToList();
This handles null KS
and IS
values, converting to empty/null values to 0
.这处理 null
KS
和IS
值,将空/空值转换为0
。
Adapt as needed.根据需要进行调整。
I've added a Constructor to your BIRIM
class that accepts arguments that match the Type of its Properties.我已经向您的
BIRIM
class 添加了一个构造函数,它接受与其属性类型匹配的 arguments。
If you cannot modify the class structure, use the syntax ( new T() { PropertyName = PropertyValue }
):如果您无法修改 class 结构,请使用语法 (
new T() { PropertyName = PropertyValue }
):
public class BIRIM
{
public BIRIM(string sbr, int sks, int sis) {
BR = sbr; KS = sks; IS = sis;
}
public string BR { get; set; }
public int KS { get; set; }
public int IS { get; set; }
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.