C# 如何使用LINQ选择*某些*项目?

C# 如何使用LINQ选择*某些*项目?,c#,.net,linq,C#,.net,Linq,如何在LINQ中编写此函数 public List<TResult> select(List<string> source) { List<TResult> result = new List<TResult>(); foreach (var a in source) { try { result.Add(TResult.Parse(a)); } catch { } } ret

如何在LINQ中编写此函数

public List<TResult> select(List<string> source)
{
    List<TResult> result = new List<TResult>();
    foreach (var a in source)
    {
        try { result.Add(TResult.Parse(a)); }
        catch { }
    }
    return result;
}
公共列表选择(列表源)
{
列表结果=新列表();
foreach(源中的变量a)
{
请尝试{result.Add(TResult.Parse(a));}
捕获{}
}
返回结果;
}
我只想选择可转换为TResult的项目。Parse()返回TResult的新实例。

一种方法是

List<TResult> result = source.Where(TResult.Parse(a) != default(TResult)).ToList()
List result=source.Where(TResult.Parse(a)!=default(TResult)).ToList()

但这假设Parse()方法不会引发异常

您可以将语句传递给LINQ方法,而不仅仅是lambda:

var results = source.Select(item => 
  {
    try
    { 
      return TResult.Parse(item);
    }
    catch
    { return null; }
  }).Where(result => result != null).ToList();

不完全是LINQ,但您可以编写一个迭代器产量解决方案,在一次传递中完成:

public static IEnumerable<TResult> SelectParse<TResult>(
                                       this IEnumerable<string> source)
{
    foreach(string a in source)
    {
        TResult parsed;
        try
        {
            parsed = TResult.Parse(a);
        }
        catch
        {
            continue;
        }
        yield return parsed;
    }
}
公共静态IEnumerable SelectParse(
这是(不可数的来源)
{
foreach(源中的字符串a)
{
TResult解析;
尝试
{
parsed=TResult.Parse(a);
}
抓住
{
继续;
}
解析收益率;
}
}
因此
List results=source.SelectParse().ToList()

但如果您的解析方法经常引发异常,那么您可能希望编写一个TryParse版本来返回成功/失败bool。(不过,这无助于编写LINQ。)



修正了try中的收益率-谢谢。与公认的解决方案相比,此解决方案的一个次要优点是它支持将null作为有效结果返回Parse,但我怀疑您是否需要/想要它。

您是否有权访问定义
Parse
的类,如果有,它是否有
TryParse
方法,或者您是否可以创建一个

    public class TResult
    {
        public static  TResult Parse(string text)
        {
            //Parse here
            return new TResult();
        }
        public static bool TryParse(string text, out TResult mc)
        {
            try
            {
                mc = Parse(text);
                return true;
            }
            catch(Exception ex)
            {
                mc = null;
                return false;
            }
        }
    }
然后

public IEnumerable选择(IEnumerable结果)
{
返回结果。选择(r=>
{
TResult item=null;
TResult.TryParse(r,项目);
退货项目;
})。其中(项=>项!=null);
}

当前代码有什么问题?它不是你想要的吗?我想写一个扩展函数到IEnumerable(SafeSelect)请注意,源和结果是不同的类型,“Where”子句返回它所应用的相同类型,因此,假设没有抛出异常,而qeustion清楚地表明它们是您忘记的“无法在带有catch子句的try块体中生成值”,但这很容易修复。哦,是的,当我把它打印出来时,我确实怀疑这是否真的合法。好地方,谢谢。
public IEnumerable<TResult> Select(IEnumerable<string> result)
    {
        return result.Select(r=>
            {
                TResult item = null;
                TResult.TryParse(r, item);
                return item;
            }).Where(item=>item != null);
    }