C# LINQ 从字符串数组中选择元素
Posted
技术标签:
【中文标题】C# LINQ 从字符串数组中选择元素【英文标题】:C# LINQ to select element from string array 【发布时间】:2022-01-01 13:51:48 【问题描述】:我有一个字符串:
private const string Codes = "2,10";
public void method()
var displayCodes = Codes.Split(',');
DemoResponse response = webService.GetResponse(); //getting response from API
if(response.Errors.Any(x => displayCodes.Contains(x.StackTrace))
int myCode = int.Parse(response.Errors.Select(x => x.StackTrace).FirstOrDefault());
这是“DemoResponse”模型:
public class DemoResponse
public bool Validate get; set;
public IEnumerable<ErrorResponse> Errors get; set;
public class ErrorResponse
public string Message get; set;
public string StackTrace get; set;
来自 API 的 DemoResponse“响应”返回结果为:(例如)
"Validate" : false,
"Errors" :
"Message" : "test1",
"StackTrace" : "2"
"Validate" : false,
"Errors" :
"Message" : "test1",
"StackTrace" : "2"
"Validate" : false,
"Errors" :
"Message" : "test1",
"StackTrace" : "95"
DemoResponse "response" 将始终仅包含来自 const string "Codes" 的代码之一,即 2 或 10。但可能包含其他代码。
如果 DemoResponse "response" 包含代码 2 作为第一个代码,则此行可以正常工作:
int myCode = int.Parse(response.Errors.Select(x => x.StackTrace).FirstOrDefault());
但如果 DemoResponse“响应”没有代码 2 作为第一个,那么我如何编写一个 LINQ 来选择代码 2 并分配给“myCode”变量? 例如:
"StackTrace" : "95",
"StackTrace" : "95",
"StackTrace" : "2"
【问题讨论】:
您需要使用Where
方法并反转解析代码以完全不处理“2”。 int myCode = response.Errors.Where(e => e.StackTrace == "2").Select(e => int.Parse(e.StackTrace)).FirstOrDefault();
- 对于任一可能的代码,请执行 int myCode = response.Errors.Where(e => displayCodes.Contains(e.StackTrace)).Select(e => int.Parse(e.StackTrace)).FirstOrDefault();
注意:如果两个代码都不存在,则您不需要 if
,myCode
将是 0
。
【参考方案1】:
需要在if条件里面为每个循环添加。
private const string Codes = "2,10";
public void method()
var displayCodes = Codes.Split(',');
DemoResponse response = webService.GetResponse(); //getting response from API
if(response.Errors.Any(x => displayCodes.Contains(x.StackTrace))
foreach (ErrorResponse item in response.Errors)
// write your logic based on your requirement
if(int.Parse(item.StackTrace) == 2)
int myCode = int.Parse(item.StackTrace);
【讨论】:
我只能为“myCode”变量设置一个值。我试过这个 -int myCode = int.Parse(response.Errors .Where(x => displayCodes.Contains(x.StackTrace)).Select(x => x.StackTrace).FirstOrDefault());
根据您的问题,需要 StackTrace=2 值作为第一优先级分配给 mycode 变量,对吗?根据您的喜好,有多种可能性 2,95,95 或 95,95,2 或 95,2,95。因此,对于您的代码中的第一个工作正常。现在对于第 2 和第 3 场景,您可以使用 foreach 和其他条件,例如 if StackTrace=2 然后分配给 mycode 否则不。检查相同的更新答案
LINQ 可以很容易地处理这个问题,foreach
循环是多余的。【参考方案2】:
在我看来,您希望从 API 接收的是一组信息,但在您的代码中,您将从 API 接收的内容映射到 @987654321 类型的单个对象@。我怀疑您实际上希望response
成为DemoResponse
s 的列表或数组。
此外,根据我对以下问题的理解:
但如果 DemoResponse “response” 没有第一个代码 2,那么我如何编写一个 LINQ 来选择 Code 2 并分配给“myCode”变量?
,您想将第一个与Codes
中的任何代码匹配的StackTrace
值分配给myCode
;而不是将 any StackTrace
值分配给 myCode
。
如果这两个假设是正确的,您可以尝试以下方法:
private const string Codes = "2,10";
public void method()
var displayCodes = Codes.Split(',');
// NOTE: response is now an array of DemoResponse;
// GetResponse()'s implementation and return type may need to be rewritten accordingly
DemoResponse[] response = webService.GetResponse();
var errors = response.SelectMany(r => r.Errors);
if (errors.Any(x => displayCodes.Contains(x.StackTrace)))
int myCode = int.Parse(errors.Select(x => x.StackTrace).First(s => displayCodes.Contains(s)));
或者,您可以循环查看堆栈跟踪而不是错误:
var stackTraces = response.SelectMany(r => r.Errors).Select(e => e.StackTrace);
if (stackTraces.Any(s => displayCodes.Contains(s)))
int myCode = int.Parse(stackTraces.First(s => displayCodes.Contains(s)));
【讨论】:
以上是关于C# LINQ 从字符串数组中选择元素的主要内容,如果未能解决你的问题,请参考以下文章
用于检查字符串列表/数组中的字符串的 C# 最佳实践 (LINQ) [关闭]