类的重载转换操作符是否分配内存或编译器是否对其进行优化?

时间:2016-04-12 13:28:05

标签: c#

让我们说我在int类型上写一个包装器。我实现了强制转换为int操作符,但是我还需要从int实现强制转换,以使这个包装器转换与分配完全一样使用。

有没有办法从int运算符实现转换而不返回我们类的新实例?或者,实现类似于实际分配新GC内存还是编译器足够智能以优化它?

更多细节:类本身跟踪值是否已更改(出于用户界面目的),因此概念上它不仅仅是值类型。

典型实现如下:

public class MyClass{
  bool m_changed = false;
  int m_val;
  public static operator MyClass(int val)
  {
     return new MyClass{m_val = val, m_changed = true}; // I would think this allocates new memory
  }

而我想要

public operator =(int val)
{
  m_changed = true;
  this.m_val = val; // no new memory allocation
}     

最终我想要

MyClass obj = new MyClass();
...
// later that day
obj = 42; // nice painless syntax, with implicit conversion

2 个答案:

答案 0 :(得分:3)

  

有没有办法从int运算符实现强制转换而不返回类的新实例?

当然,返回null并且您不会返回该类的新实例。我认为从技术上讲,您还可以使用某种对象池或其他类似策略来返回一些已存在的对象,从而不返回 new 对象。也就是说,从您正在做的事情的声音来看,您几乎肯定想要返回该类型的新实例。

  

或者,是实现像实际分配新GC内存还是编译器足够聪明以优化它?

围绕静态方法只是一些语法糖。就像任何其他方法一样,无论你告诉它在实现中做什么,它都会做。纯粹的调用方法没有分配 required ,但典型的实现是分配一个返回的对象。 GC没有任何东西可以在这里“优化”;它完全取决于您选择提供的操作符的实现。

答案 1 :(得分:0)

我去了

obj.SetValue(42);

而不是

obj = 42; // nice painless syntax, with implicit conversion

因为这清楚地说明了发生了什么。使用=语法,读者永远不会期望保留实例,即使您找到了一种方法。

如果您希望obj的用户可以看到该值,您还可以找一个属性。如果没有,我更喜欢一种方法,因为只有setter属性才会感觉很奇怪。