C# 检查字符串是否可以转换为给定类型
我必须创建一个API,在该API中,我需要向用户提供正确的消息。如果用户没有在GET请求中提供必需的参数,我还需要确保用户在参数中提供了正确的值,这些值可以是整数、字符串、日期或枚举 因此,我创建了一个类SearchParameters,其中列出了请求参数的相关信息C# 检查字符串是否可以转换为给定类型,c#,C#,我必须创建一个API,在该API中,我需要向用户提供正确的消息。如果用户没有在GET请求中提供必需的参数,我还需要确保用户在参数中提供了正确的值,这些值可以是整数、字符串、日期或枚举 因此,我创建了一个类SearchParameters,其中列出了请求参数的相关信息 private static class SearchParameters { public static List<ParamInfo> ParamList = new List<ParamInfo>
private static class SearchParameters
{
public static List<ParamInfo> ParamList = new List<ParamInfo>
{
new ParamInfo {Name ="location", IsMandatory = true , ExpecteDataType = typeof(ulong) } ,
new ParamInfo {Name ="service", IsMandatory = true , ExpecteDataType = typeof(ServiceType)} ,
new ParamInfo {Name ="start", IsMandatory = true , ExpecteDataType = typeof(DateTimeOffset)} ,
new ParamInfo {Name ="appointmentType", IsMandatory = true , ExpecteDataType = typeof(AppointmentType)} ,
new ParamInfo {Name ="status", IsOptional = true , ExpecteDataType = typeof(string)} ,
new ParamInfo {Name ="end", IsOptional = true , ExpecteDataType = typeof(DateTimeOffset)} ,
new ParamInfo {Name ="clinicianGender", IsOptional = true , ExpecteDataType = typeof(AdministrativeGender)} ,
new ParamInfo {Name ="_sort", IsForSorting = true , ExpecteDataType = typeof(string)},
new ParamInfo {Name ="_count", IsForPaging = true , ExpecteDataType = typeof(uint)}
};
}
当用户请求我在元组列表中提供参数时,Item1
和Item2
都是字符串,Item1
是查询参数的名称,Item2
是用户提供的值
如何确保参数值(即Item2
)的数据类型正确
我试过这样的方法:
// Data tye verification
foreach (ParamInfo info in SlotSearchParameters.ParamList)
{
Tuple<string, string> param = searchparams.Parameters.Where(x => x.Item1.ToLower() == info.Name).FirstOrDefault();
if (param != null)
{
Type expectedType = info.ExpecteDataType;
// how can we check if the value of type of x.Item1 is as expected
// Can't procede
}
}
foreach (ParamInfo info in SlotSearchParameters.ParamList)
{
Tuple<string, string> param = searchparams.Parameters.Where(x => x.Item1.ToLower() == info.Name).FirstOrDefault();
if (param != null &&
Validator(x.Item1) //
{
//whatever
}
}
//数据类型验证
foreach(SlotSearchParameters.ParamList中的ParamInfo信息)
{
Tuple param=searchparams.Parameters.Where(x=>x.Item1.ToLower()==info.Name.FirstOrDefault();
如果(参数!=null)
{
类型expectedType=info.ExpecteDataType;
//如何检查x.Item1类型的值是否如预期的那样
//无法继续
}
}
但是由于
x.Item1
始终是提供的值的字符串表示形式,可以是Date、Int或string等,我不知道该怎么办?出于您问题中所述的目的,您应该使用Parse()
(re:)或TryParse()
(re:)方法,例如int32.Parse([your_string])代码>
希望这会有所帮助。您可以向ParamInfo
类添加验证程序:
public class ParamInfo
{
public string Name { get; set; }
public bool IsMandatory { get; set; }
public bool IsRequired { get; set; }
public bool IsOptional { get; set; }
public bool IsForSorting { get; set; }
public bool IsForPaging { get; set; }
public Type ExpecteDataType { get; set; }
public Predicate<string> Validator { get; set; }
}
公共类ParamInfo
{
公共字符串名称{get;set;}
公共布尔是强制性的{get;set;}
需要公共布尔值{get;set;}
公共布尔等民族{get;set;}
公共bool用于排序{get;set;}
公共bool用于分页{get;set;}
公共类型ExpecteDataType{get;set;}
公共谓词验证器{get;set;}
}
现在:
public static List<ParamInfo> ParamList = new List<ParamInfo>
{
new ParamInfo { Name ="location",
IsMandatory = true,
ExpecteDataType = typeof(ulong),
Validator = s => s != null && ulong.TryParse(s, out var _); }
public static List ParamList=新列表
{
新的ParamInfo{Name=“location”,
IsMandatory=正确,
ExpecteDataType=类型(ulong),
Validator=s=>s!=null&&ulong.TryParse(s,out var)}
您可以这样使用它:
// Data tye verification
foreach (ParamInfo info in SlotSearchParameters.ParamList)
{
Tuple<string, string> param = searchparams.Parameters.Where(x => x.Item1.ToLower() == info.Name).FirstOrDefault();
if (param != null)
{
Type expectedType = info.ExpecteDataType;
// how can we check if the value of type of x.Item1 is as expected
// Can't procede
}
}
foreach (ParamInfo info in SlotSearchParameters.ParamList)
{
Tuple<string, string> param = searchparams.Parameters.Where(x => x.Item1.ToLower() == info.Name).FirstOrDefault();
if (param != null &&
Validator(x.Item1) //
{
//whatever
}
}
foreach(SlotSearchParameters.ParamList中的ParamInfo信息)
{
Tuple param=searchparams.Parameters.Where(x=>x.Item1.ToLower()==info.Name.FirstOrDefault();
if(param!=null&&
验证器(x.Item1)//
{
//随便
}
}
}
如何确保参数(即Item2)的值是正确的数据类型
您可能会让用户很难实际输入错误的数据类型。例如,如果他们在表单中键入内容,而您要求输入日期–如果他们在该字段中键入一些不合理的内容,请将其设置为无法提交表单
如果他们输入了一些不感兴趣的内容,或者
如果输入值不真实,可以阻止创建ParamInfo对象。有关一些示例,请参见下文
旁注:您在ParamInfo类中实际将数据存储在哪里?如果您实际上将变量存储为int、date或enum等,那么使用此变量将无需使用ExpectedDataType变量。我希望这是有意义的。换句话说,是否要将item1.value作为字符串存储在ParamInfo中类还是非类?还是要将其存储为实际数字、日期或枚举
用户是否可能意外输入错误的ParamInfo.Name值
无论如何,这里有一些想法希望能帮助你:
internal class Program
{
private static void Main(string[] args)
{
List<Tuple<string, string>> userInputValues = new List<Tuple<string, string>>(); // obviously implement the correct user values here
// This is the money below.
// you'll have only valid ParamInfo objects here:
List<ParamInfo> paramFactory = new ParamInfoFactory(userInputValues).ValidParameters;
}
public class ParamInfo
{
public string Name { get; set; }
public bool IsMandatory { get; set; }
public bool IsRequired { get; set; }
public bool IsOptional { get; set; }
public bool IsForSorting { get; set; }
public bool IsForPaging { get; set; }
public Type ExpecteDataType { get; set; } // <--- you really don't need this.
// where are you storing the item1.value?
// are you storing it as a string, or as the proper type that it represents?
}
public class ParamInfoFactory
{
public List<ParamInfo> ValidParameters { get; set; }
public ParamInfoFactory(List<Tuple<string, string>> userSuppliedValues)
{
ValidParameters = new List<ParamInfo>();
foreach (Tuple<string, string> userValue in userSuppliedValues)
{
if (UserInputValuesAreValid(userValue))
{
// all the values are valid. you can now create and add the parameters to your list.
// remember to instantiate it as you wish with the right values etc in there.
ValidParameters.Add(new ParamInfo());
}
}
}
private bool UserInputValuesAreValid(Tuple<string, string> userValue)
{
return IsNameValid(userValue.Item1) && IsDataValid(userValue.Item2);
}
private bool IsDataValid(string data)
{
return IsValidDate(data) || IsValidNumber(data); // you can also implement the IsValidEnum or any other method you want
}
private static bool IsValidDate(string data)
{
DateTime dateValue;
bool isDate = DateTime.TryParse(data, out dateValue);
return isDate;
}
//private static bool IsEnum(string data)
//{
// Colors colorValue;
// bool isEnum = Enum.TryParse(data, out colorValue);
// return isEnum;
//}
private static bool IsValidNumber(string data)
{
int number;
bool isNumber = Int32.TryParse(data, out number);
return isNumber;
}
private bool IsNameValid(string userInputName)
{
return SearchParameters.ParamList.Any(paramInfo => paramInfo.Name == userInputName.ToLower());
}
private static class SearchParameters
{
public static List<ParamInfo> ParamList = new List<ParamInfo>
{
new ParamInfo {Name ="location", IsMandatory = true , ExpecteDataType = typeof(ulong) } ,
new ParamInfo {Name ="service", IsMandatory = true , ExpecteDataType = typeof(ServiceType)} ,
new ParamInfo {Name ="start", IsMandatory = true , ExpecteDataType = typeof(DateTimeOffset)} ,
new ParamInfo {Name ="appointmentType", IsMandatory = true , ExpecteDataType = typeof(AppointmentType)} ,
new ParamInfo {Name ="status", IsOptional = true , ExpecteDataType = typeof(string)} ,
new ParamInfo {Name ="end", IsOptional = true , ExpecteDataType = typeof(DateTimeOffset)} ,
new ParamInfo {Name ="clinicianGender", IsOptional = true , ExpecteDataType = typeof(AdministrativeGender)} ,
new ParamInfo {Name ="_sort", IsForSorting = true , ExpecteDataType = typeof(string)},
new ParamInfo {Name ="_count", IsForPaging = true , ExpecteDataType = typeof(uint)}
};
}
}
}
内部类程序
{
私有静态void Main(字符串[]args)
{
List userInputValues=new List();//显然在这里实现正确的用户值
//这是下面的钱。
//此处只有有效的ParamInfo对象:
List paramFactory=新的ParamInfoFactory(userInputValues).ValidParameters;
}
公共类ParamInfo
{
公共字符串名称{get;set;}
公共布尔是强制性的{get;set;}
需要公共布尔值{get;set;}
公共布尔等民族{get;set;}
公共bool用于排序{get;set;}
公共bool用于分页{get;set;}
公共类型ExpecteDataType{get;set;}//我有一个字符串和一个类型变量,类型变量可以是string、Int、DateTime等类型。我们在类型类上没有任何直接的解析方法。那么您的业务逻辑有严重缺陷,简单明了。您应该先修复您的业务逻辑。如果您有更多问题,请标记此问题的答案并将其分开发布非常感谢。非常棒!您的解决方案非常优雅。我曾考虑使用反射,但使用委托的建议确实简化了一切。我没有使用C#7,因此无法使用不在乎(解析结果)由于TryParse方法的特性,我通过在String类上添加一些扩展方法来实现这一点。谢谢you@JavidAhmad很高兴它有帮助!