Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/322.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何获得扩展方法来更改原始对象?_C#_Generics_Object_Extension Methods - Fatal编程技术网

C# 如何获得扩展方法来更改原始对象?

C# 如何获得扩展方法来更改原始对象?,c#,generics,object,extension-methods,C#,Generics,Object,Extension Methods,我希望能够编写扩展方法,这样我就可以说: lines.ForceSpaceGroupsToBeTabs(); 而不是: lines = lines.ForceSpaceGroupsToBeTabs(); Tone TTtwo 但是,以下代码当前输出: ....one ........two 而不是: lines = lines.ForceSpaceGroupsToBeTabs(); Tone TTtwo 我必须在以下代码中更改什么才能将其输出: Tone TTtwo (注意,对于可

我希望能够编写扩展方法,这样我就可以说:

lines.ForceSpaceGroupsToBeTabs();
而不是:

lines = lines.ForceSpaceGroupsToBeTabs();
Tone
TTtwo
但是,以下代码当前输出:

....one
........two
而不是:

lines = lines.ForceSpaceGroupsToBeTabs();
Tone
TTtwo
我必须在以下代码中更改什么才能将其输出:

Tone
TTtwo
(注意,对于可见性,
=space,T=\T
):

使用系统;
使用System.Collections.Generic;
命名空间TestExtended82343
{
班级计划
{
静态void Main(字符串[]参数)
{
列表行=新列表();
行。添加(“……一”);
行。添加(“……两行”);
lines.ForceSpaceGroupsToBeTabs();
lines.ForEach(l=>Console.WriteLine(l));
Console.ReadLine();
}
}
公共静态类助手
{
公共静态void ForceSpaceGroupsToBeTabs(此列表原始行)
{
字符串空格组=新字符串('.',4);
列表行=新列表();
foreach(原始数据线中的原始数据线变量)
{
行。添加(原始行。替换(空格组,“T”);
}
原始线=线;
}
}
}

您必须修改传递给扩展方法的
列表的内容,而不是保存列表引用的变量:

public static void ForceSpaceGroupsToBeTabs(this List<string> lines)
{
    string spaceGroup = new String('.', 4);
    for (int i = 0; i < lines.Count; i++)
    {
        lines[i] = lines[i].Replace(spaceGroup, "T");
    }
}
publicstaticvoidforcespacegroupstobetabs(此列表行)
{
字符串空格组=新字符串('.',4);
对于(int i=0;i
您必须更改原始列表的内容-只需重新分配参数使其具有不同的值是行不通的。大概是这样的:

public static void ForceSpaceGroupsToBeTabs(this List<string> lines)
{
    string spaceGroup = new String('.', 4);
    for (int i = 0; i < lines.Count; i++)
    {
        lines[i] = lines[i].Replace(spaceGroup, "T");
    }
}
。。。因为这就是代码被有效地翻译成的内容。它是一种扩展方法,这一事实没有什么特别之处;如果更改代码使“普通”静态方法可以工作,那么它也可以作为扩展方法工作。如注释中所述,使用扩展方法不能做的一件事是将第一个参数设置为
ref
参数


(编辑:我意识到这与dtb发布的代码完全相同,尽管我们是独立到达那里的。无论如何,我保留这个答案,因为它不仅仅是代码。)

如果它是引用类型,你必须更改它的内容。如果你传递的是一个值类型,那你就不走运了。扩展方法的存在是为了支持C#中的函数范式,而这些函数范式本质上倾向于类型的不变性,因此无法更改调用扩展方法的值


换句话说,虽然你可以这样做,但它可能与函数式编程的“精神”不符。

这不是完全相同的代码,你有spaceGroup(“T”),你是在想别的什么,还是只是打字错误(它没有编译)@Jon:区别在于,通过Helpers.ForceSpaceGroupsToBeTabs,他可以将参数更改为“ref”参数,在这种情况下,他的现有代码将产生预期效果。不过,使用扩展方法时,您无法使参数引用…@Edward:只是输入错误。我认为这个答案的第二部分有误导性。扩展方法的主要用例是在接口上,接口是引用类型,在这些情况下,对变异没有特殊限制:功能与普通方法相同,即
a.SomeMethod()不能使
a
引用其他对象,但可以更改它引用的对象。确实如此。不能切换“扩展”引用对象,但可以更改对象的内容