Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

IntelliSense error: a reference cannot be bound to an initonly field?

Tags:

.net

c++-cli

I have a C++/CLI class like this:

// MyClass.h
#pragma once

namespace MyNamespace {
    using namespace System;

    public ref class MyClass {
    private:
        MyClass();
        IntPtr m_ptr;
    };
}

// MyClass.cpp
#include "MyClass.h"
using namespace System;

namespace MyNamespace {
    MyClass::MyClass() {
        m_ptr = IntPtr::Zero;
    }
}

The project compiles without errors or warnings, however the line m_ptr = IntPtr::Zero is always underlined red with an IntelliSense error: "a reference cannot be bound to an initonly field". What gives? How can I get rid of this?

This is in Visual Studio 2012 Premium Edition but the Platform Toolset is Visual Studio 2008 (v90).

like image 761
Asik Avatar asked Jun 04 '13 14:06

Asik


1 Answers

Well, it is a bug in the IntelliSense parser. Written by the Edison Design Group. Pretty famous for writing C++ front-ends but C++/CLI has certainly given them a workout. It has trouble with initonly fields in general (IntPtr::Zero is initonly), something similar here but not otherwise related to this bug. Not having any equivalent in C++ may well be a contributing factor.

It doesn't get put the test much with code like this, the assignment is entirely superfluous. The CLR already makes a hard guarantee that all fields in a managed class are zero-initialized.

So workaround #1 is to just omit the assignment, it doesn't do anything useful.

Workaround #2 is to use the standard C++ constructor initialization syntax:

   MyClass::MyClass() : m_ptr(IntPtr::Zero) {}

Workaround #3, way at the bottom of the list is to initialize it like this, avoiding the initonly field:

MyClass::MyClass() {
    m_ptr = IntPtr();
}

But I'd certainly recommend #1.

like image 148
Hans Passant Avatar answered Oct 11 '22 16:10

Hans Passant