如何使用 Func<> 创建 linq 扩展方法?
How to create a linq extension method with Func<>?
我创建了可以像这样使用的扩展方法:
string returnValue = numbers.At(separator, index).Slice();
但我想这样创建:
string returnValue = numbers.At(s => '.').Slice();
这是另一个代码。
public class StringParameters
{
public string Text { get; set; }
public int Position { get; set; }
public StringParameters(string text, int position)
{
this.Text = text;
this.Position = position;
}
}
public static StringParameters At(this string text, char c)
{
int index = text.IndexOf(c);
if (index > 0)
{
int index2 = text.IndexOf(c, index + 1);
if (index2 > index)
{
text = text.Substring(index2, text.Length - index2);
}
return new StringParameters(text, index2 + 1);
}
return new StringParameters(null, -1);
}
public static string Slice(this StringParameters parameters)
{
return parameters.Text.Substring(parameters.Position);
}
编辑: 我编辑了代码并将 ... 替换为 "something here"。我仍然不完全了解它应该在那里。我的期望是这个方法应该更有用。
编辑 2: 我现在知道我想用我的代码创建什么。我希望能够做出这样的事情:
string returnValue = numbers.At(s, i => GetStringParameter()).Slice();
编辑 3: 我对代码进行了一些编辑。现在可能会更清楚我想要实现的目标。
编辑 4: 更正了上面代码中的一个错误。
我想你想要
string returnValue = numbers.At(s, i => GetStringParameter()).Slice();
使用具有签名的 Slice
扩展方法:
public static string Slice(this StringParameters parameters)
即你想要
StringParameters stringParameters = numbers.At(s, i => GetStringParameter());
string returnValue = stringParameters.Slice();
听起来您需要重载您的扩展方法,At
,才能拥有像这样的签名:
public static StringParameters At(this string text, S s, Func<T, U> func)
其中 S
是您传入的 s
的类型,T
是您 Func 的输入,U
是Func.
的输出类型
在 At
方法中,您可以像调用方法一样使用 Func,例如
Func<int, string> func = (int)i => i.ToString();
string s = func(123); // s == "123"
我不清楚你想要实现什么(start
参数,你想用函数替换,在 At
函数的任何地方都没有使用),但这是一个带有 Func<> 参数的示例扩展函数:
public static StringParameters At(this string text, char c, Func<int> startFunc)
{
int start = startFunc();
int index = text.IndexOf(c);
if (index > 0)
{
int index2 = text.IndexOf(c, index + 1);
if (index2 > index)
{
text = text.Substring(0, text.Length - index2);
}
return new StringParameters(text, index2 + 1);
}
return new StringParameters(null, -1);
}
用法:
string returnValue = numbers.At(s, () => GetStartIndex()).Slice();
你不需要在这里 i =>
直到你有一个参数,你将传递给 At
函数内的 Func<>
。
当您调用 int start = startFunc();
时,您作为参数传递给 At
的函数(在我的示例中为 GetStartIndex()
)将被调用,其 return 值将是设置为 start
变量。
在 Aleksey Shubin 和其他人的帮助下,我终于找到了解决方案。最终代码如下所示:
public static class Linq
{
public class StringParameters
{
public string Text { get; set; }
public int Position { get; set; }
public StringParameters(string text, int position)
{
this.Text = text;
this.Position = position;
}
}
public static StringParameters At(this string text, Func<char> func)
{
char c = func();
int index = text.IndexOf(c);
if (index > 0)
{
int index2 = text.IndexOf(c, index + 1);
if (index2 > index)
{
text = text.Substring(index2, text.Length - index2);
}
return new StringParameters(text, index2 + 1);
}
return new StringParameters(null, -1);
}
public static string Cut(this StringParameters parameters)
{
return parameters.Text.Substring(parameters.Position);
}
}
可以这样使用:
string returnValue = "132.465..646.656.45".At(() => '.').Cut();
这 return 的值为 6.45。它应该 return 656.45 或 132.465 的值,但这很容易。谢谢大家的帮助。
我创建了可以像这样使用的扩展方法:
string returnValue = numbers.At(separator, index).Slice();
但我想这样创建:
string returnValue = numbers.At(s => '.').Slice();
这是另一个代码。
public class StringParameters
{
public string Text { get; set; }
public int Position { get; set; }
public StringParameters(string text, int position)
{
this.Text = text;
this.Position = position;
}
}
public static StringParameters At(this string text, char c)
{
int index = text.IndexOf(c);
if (index > 0)
{
int index2 = text.IndexOf(c, index + 1);
if (index2 > index)
{
text = text.Substring(index2, text.Length - index2);
}
return new StringParameters(text, index2 + 1);
}
return new StringParameters(null, -1);
}
public static string Slice(this StringParameters parameters)
{
return parameters.Text.Substring(parameters.Position);
}
编辑: 我编辑了代码并将 ... 替换为 "something here"。我仍然不完全了解它应该在那里。我的期望是这个方法应该更有用。
编辑 2: 我现在知道我想用我的代码创建什么。我希望能够做出这样的事情:
string returnValue = numbers.At(s, i => GetStringParameter()).Slice();
编辑 3: 我对代码进行了一些编辑。现在可能会更清楚我想要实现的目标。
编辑 4: 更正了上面代码中的一个错误。
我想你想要
string returnValue = numbers.At(s, i => GetStringParameter()).Slice();
使用具有签名的 Slice
扩展方法:
public static string Slice(this StringParameters parameters)
即你想要
StringParameters stringParameters = numbers.At(s, i => GetStringParameter());
string returnValue = stringParameters.Slice();
听起来您需要重载您的扩展方法,At
,才能拥有像这样的签名:
public static StringParameters At(this string text, S s, Func<T, U> func)
其中 S
是您传入的 s
的类型,T
是您 Func 的输入,U
是Func.
在 At
方法中,您可以像调用方法一样使用 Func,例如
Func<int, string> func = (int)i => i.ToString();
string s = func(123); // s == "123"
我不清楚你想要实现什么(start
参数,你想用函数替换,在 At
函数的任何地方都没有使用),但这是一个带有 Func<> 参数的示例扩展函数:
public static StringParameters At(this string text, char c, Func<int> startFunc)
{
int start = startFunc();
int index = text.IndexOf(c);
if (index > 0)
{
int index2 = text.IndexOf(c, index + 1);
if (index2 > index)
{
text = text.Substring(0, text.Length - index2);
}
return new StringParameters(text, index2 + 1);
}
return new StringParameters(null, -1);
}
用法:
string returnValue = numbers.At(s, () => GetStartIndex()).Slice();
你不需要在这里 i =>
直到你有一个参数,你将传递给 At
函数内的 Func<>
。
当您调用 int start = startFunc();
时,您作为参数传递给 At
的函数(在我的示例中为 GetStartIndex()
)将被调用,其 return 值将是设置为 start
变量。
在 Aleksey Shubin 和其他人的帮助下,我终于找到了解决方案。最终代码如下所示:
public static class Linq
{
public class StringParameters
{
public string Text { get; set; }
public int Position { get; set; }
public StringParameters(string text, int position)
{
this.Text = text;
this.Position = position;
}
}
public static StringParameters At(this string text, Func<char> func)
{
char c = func();
int index = text.IndexOf(c);
if (index > 0)
{
int index2 = text.IndexOf(c, index + 1);
if (index2 > index)
{
text = text.Substring(index2, text.Length - index2);
}
return new StringParameters(text, index2 + 1);
}
return new StringParameters(null, -1);
}
public static string Cut(this StringParameters parameters)
{
return parameters.Text.Substring(parameters.Position);
}
}
可以这样使用:
string returnValue = "132.465..646.656.45".At(() => '.').Cut();
这 return 的值为 6.45。它应该 return 656.45 或 132.465 的值,但这很容易。谢谢大家的帮助。