Arm*_*ino 3 c# generics refactoring unity-game-engine
我正在与Unity进行RTS游戏.我的游戏中有很多类型的资源,例如树,农场.每个资源都是一个GameObject,并拥有自己的主脚本来控制它.
防爆.我想要收获一棵树,我称之为.
gameObject.GetComponent<Tree>().Harvest();
Run Code Online (Sandbox Code Playgroud)
如果我想收获农场,我会调用相同的脚本,但将"Tree"更改为"Farm",这很好,但代码将被复制.所以我通过使用这样的泛型方法来抽象它.
void Harvest<T>(){
gameObject.GetComponent<T>().Harvest();
}
Run Code Online (Sandbox Code Playgroud)
但是C#编译器不允许我这样做.我想知道是否可以定义使用泛型方法的泛型方法?如果没有,有没有办法像这样抽象我的代码?谢谢.
错误信息:
'T'不包含'Harvest'的定义,并且没有扩展方法'Harvest'可以找到接受类型'T'的第一个参数(你是否缺少using指令或汇编引用?)[Assembly-CSharp]
问题在于......
void Harvest<T>(){
gameObject.GetComponent<T>().Harvest();
}
Run Code Online (Sandbox Code Playgroud)
... C#编译器不知道将使用哪种具体类型T.因此,它无法知道将会有一个方法Harvest可用,也不知道它的确切声明(它返回void或者bool还是其他什么东西?它有没有可选参数?).因为C#是一种强类型语言,所以必须在编译时知道它.这使您确信一切都会在运行时顺利进行.
解决方案是通过指定泛型类型约束为编译器提供提示.要做到这一点,你必须声明一个接口,让带有Harvest方法的组件实现它.
public interface IHarvestable
{
void Harvest();
}
Run Code Online (Sandbox Code Playgroud)
用以下内容指定约束:
void Harvest<T>() where T : IHarvestable
{
gameObject.GetComponent<T>().Harvest();
}
Run Code Online (Sandbox Code Playgroud)
在您控制基类的其他情况下,您还可以在基类中声明所需的方法(可能是抽象的),并在泛型类型约束中指定基类而不是接口.
| 归档时间: |
|
| 查看次数: |
58 次 |
| 最近记录: |