根据在多个单元格中拆分字符串将一行拆分为多行
Split One Row into many based on splitting string in multiple cells
尝试根据两个单元格中的字符串将一行分成多行。它类似于问题
LINQ to separate column value of a row to different rows in .net
但我需要根据产品和成本列进行拆分,而不是仅根据产品列进行拆分
SNo.
Product
Cost
1
colgate,closeup,pepsodent
50,100,150
2
rin,surf
100
进入
SNo.
Product
Cost
1
colgate
50
1
closeup
100
1
pepsodent
150
2
rin
100
2
surf
100
我正在使用 Linq to Object Entity Framework
尝试以下操作。由于您没有提供任何模型,因此名称可能不准确。
var loaded = ctx.Products.ToList();
var query =
from p in loaded
from sp in p.Product.Split(',').Zip(p.Cost.Split(','), (p, c) => (p, c))
select new
{
Sno = p.Sno,
Product = sp.p,
Cost = sp.c
};
var splitted = query.ToList();
使用@SvyatoslavDanyliv 命名,这里是一个答案:
var loaded = ctx.Products.ToList();
var query =
from p in loaded
from sp in p.Product.Split(',').Zip(p.Cost.Split(','), (p, c) => (p, c))
select new
{
Sno = p.Sno,
Product = sp.p,
Cost = sp.c
};
var splitted = query.ToList();
我觉得有点复杂。我更喜欢使用扩展方法来创建 Zip
的变体,它重复较短序列的最后一个元素以匹配较长序列:
public static class EnumerableExt {
public static IEnumerable<(T1 First,T2 Second)> ZipExtend<T1,T2>(this IEnumerable<T1> s1, IEnumerable<T2> s2) {
var s1e = s1.GetEnumerator();
var s2e = s2.GetEnumerator();
T1 s1eLast = default;
T2 s2eLast = default;
bool has_s2 = false;
if (s1e.MoveNext()) {
do {
s1eLast = s1e.Current;
if (s2e.MoveNext()) {
s2eLast = s2e.Current;
has_s2 = true;
}
else if (!has_s2)
yield break;
yield return (s1eLast, s2eLast);
} while (s1e.MoveNext());
if (has_s2)
while (s2e.MoveNext())
yield return (s1eLast, s2e.Current);
}
yield break;
}
}
那么答案是:
var query =
from p in loaded
from pr in p.Product.Split(',').ZipExtend(p.Cost.Split(','))
select new
{
Sno = p.Sno,
Product = pr.First,
Cost = pr.Second
};
var splitted = query.ToList();
尝试根据两个单元格中的字符串将一行分成多行。它类似于问题 LINQ to separate column value of a row to different rows in .net 但我需要根据产品和成本列进行拆分,而不是仅根据产品列进行拆分
SNo. | Product | Cost |
---|---|---|
1 | colgate,closeup,pepsodent | 50,100,150 |
2 | rin,surf | 100 |
进入
SNo. | Product | Cost |
---|---|---|
1 | colgate | 50 |
1 | closeup | 100 |
1 | pepsodent | 150 |
2 | rin | 100 |
2 | surf | 100 |
我正在使用 Linq to Object Entity Framework
尝试以下操作。由于您没有提供任何模型,因此名称可能不准确。
var loaded = ctx.Products.ToList();
var query =
from p in loaded
from sp in p.Product.Split(',').Zip(p.Cost.Split(','), (p, c) => (p, c))
select new
{
Sno = p.Sno,
Product = sp.p,
Cost = sp.c
};
var splitted = query.ToList();
使用@SvyatoslavDanyliv 命名,这里是一个答案:
var loaded = ctx.Products.ToList();
var query =
from p in loaded
from sp in p.Product.Split(',').Zip(p.Cost.Split(','), (p, c) => (p, c))
select new
{
Sno = p.Sno,
Product = sp.p,
Cost = sp.c
};
var splitted = query.ToList();
我觉得有点复杂。我更喜欢使用扩展方法来创建 Zip
的变体,它重复较短序列的最后一个元素以匹配较长序列:
public static class EnumerableExt {
public static IEnumerable<(T1 First,T2 Second)> ZipExtend<T1,T2>(this IEnumerable<T1> s1, IEnumerable<T2> s2) {
var s1e = s1.GetEnumerator();
var s2e = s2.GetEnumerator();
T1 s1eLast = default;
T2 s2eLast = default;
bool has_s2 = false;
if (s1e.MoveNext()) {
do {
s1eLast = s1e.Current;
if (s2e.MoveNext()) {
s2eLast = s2e.Current;
has_s2 = true;
}
else if (!has_s2)
yield break;
yield return (s1eLast, s2eLast);
} while (s1e.MoveNext());
if (has_s2)
while (s2e.MoveNext())
yield return (s1eLast, s2e.Current);
}
yield break;
}
}
那么答案是:
var query =
from p in loaded
from pr in p.Product.Split(',').ZipExtend(p.Cost.Split(','))
select new
{
Sno = p.Sno,
Product = pr.First,
Cost = pr.Second
};
var splitted = query.ToList();