【问题标题】:Passing a generic pointer to a method in c#将泛型指针传递给 C# 中的方法
【发布时间】:2012-11-06 00:22:03
【问题描述】:

我创建了一个泛型类型来充当指针,以便我可以通过引用传递。 (也许有一种更简单的方法可以做到这一点,但我想强调我这样做是为了更多地了解泛型和通过引用传递,如果这有意义的话,这不是完成任务的最有效方式。)

这是我为泛型类型编写的代码

class GenericPointer<T> {
    public T item;
    public void setItem(T i){ item = i; }
    public T getItem(){ return item; }
}

在我的程序中,我创建了一个名为“intPointer”的此类实例。值 143 是任意的。

GenericPointer<int> intPointer = new GenericPointer<int>();
intPointer.setItem(143);
Console.WriteLine(intPointer.getItem());

以上代码运行正常,设置并返回值143。

我现在想将这个“intPointer”传递给一个增加它的方法,然后再次打印该值。

所以我写了一个叫addone()的方法

public void addone(int i) { i ++; }

现在我想进行以下调用(记住我已经将值设置为 143):

Console.WriteLine(intPointer.getItem());
addone(intPointer);
Console.WriteLine(intPointer.getItem());

我期望看到的是 143,然后是 144,但是我收到以下错误:

The best overloaded method match for 'Notes.Program.addone(int)' has some invalid arguments

和:

cannot convert from 'Notes.GenericPointer<int>' to 'int'

任何帮助将不胜感激!

【问题讨论】:

  • 这个问题太宽泛了...正确的答案需要对大量 C# 的完整解释...
  • 为什么不简单地使用 ref 关键字呢? msdn.microsoft.com/en-us/library/14akc2c7.aspx 这里也是一个很好的答案:stackoverflow.com/a/3539299/578843
  • @MiMo 我想我在这里对我的问题给出了一个非常具体的解释。这个网站是为了学习和解决问题而存在的。没有人强迫你阅读或居高临下。我不需要有人握住我的手,只要朝着正确的方向推动即可。幸运的是,还有其他人愿意提供帮助。如果你没有什么可说的,那就帮别人一个忙,把你的 cmets 留给自己。

标签: c# generics pointers


【解决方案1】:

我将首先更正您的一些术语:您没有使用指针。 C# 确实支持指针,但使用 unsafe 关键字,它们是真正的指针(例如,可以直接操作的整数内存地址)。您编写的代码只是一个装箱对象的示例。

.NET 已经支持装箱,通过转换为Object;但是不建议也不需要这样做,因为 ref 关键字可以解决您尝试“修复”的问题。

使用ref 关键字来描述一个值类型的参数,该参数应该按引用而不是按值传递。所有其他语义保持不变,如下所示:

void Foo() {
    int x = 123;
    Bar(ref x);
    Console.Write( x ); // prints "124".
}
void Bar(ref int x) {
    x++;
}

我还有一些注意事项:

  1. C# 和 .NET 约定规定所有公共成员(方法、属性、字段等)都应使用 TitleCase,而不是 camelCase(即确保首字母大写)。
  2. 不鼓励使用简单的 getter 和 setter 方法,而是使用 Properties(尽管我注意到您不能将 ref 参数与属性一起使用)。
  3. 您收到错误是因为 intPointer 的类型不是 int,而是您的班级 GenericPointer&lt;int&gt;

【讨论】:

  • 我认为ref需要在调用Bar时使用,如:Bar(ref x);
  • @Dai 首先,感谢您对术语的澄清,我仍然收到错误消息。除了现在它说它不能转换为'ref int'我误会了吗?所以我做了以下更改:'addone(ref intPointer);'和 'public void addone(ref int i)' '{' 'i ++;' '}'
  • 显然我还没有弄清楚如何将代码放在评论中..这些天我想通了
  • 我的意思是你应该完全摆脱你的GenericPointer 类,而只使用ref int
  • @Dai 我明白了。谢谢您的帮助!我用你的建议让它工作了。
【解决方案2】:

虽然 GenericPointer 包装了一个 int,但它实际上并不是一个 int,因此不能将其视为一个 int。它具有 int 属性。

想象一下,如果 GenericPointer 包装了一个字符串。 AddOne 会对此做什么。

您可以对类的属性进行操作,但不能将整个类视为其泛型类型。

可以编写一个 AddOne 方法,该方法接受一个 Generic Pointer 参数,然后检查它的 intyness,如果它是 int,则将其添加到内部项。我确信这不是一个好主意。

你真正想用这个 GenericPointer 实现什么?

【讨论】:

  • 老实说,我在学习这门语言时只是在尝试使用 c#。我理解你所说的关于它是通用的并试图执行加法的问题。我希望能够做的是传递值并让程序以与我尝试将字符串传递给将尝试增加该字符串的方法相同的方式做出反应。因为那显然是不可能的,我会得到一个错误。这甚至可能吗?还是我到达这里?
【解决方案3】:

如果您希望参数是值类型(字符串、int、bool 等)时被引用,那么将您的参数设置为:

public void addone(ref int i)
{
    i++;
}

然后像这样调用方法:

addone(ref variableInt);

您还可以查看 this 以了解如何使您的课程作为特定类型工作。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-12-11
    • 2021-08-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-27
    相关资源
    最近更新 更多