“const方法”编译读取成员变量的错误

时间:2017-05-29 05:57:47

标签: c++ const stdvector

我想知道为什么我得到第一个“const方法”的编译错误,而第二个是OK。

typedef struct xyz{
    uint16_t xyz1[16];
}XYZ;

class A {
public :
    A() :m_a1(4) { m_a2 = new XYZ[4]; }
    void getSomething() const
    {
        uint16_t* p = m_a1[0].xyz1; //error: invalid conversion from 
                                    //'const uint16_t* {aka const short unsigned int*}' 
                                    //to 'uint16_t* {aka short unsigned int*}'
    }
    voi getSomething2() const
    {
        uint16_t* p = m_a2[0].xyz1; //compile OK
    }
private:
    vector<XYZ> m_a1;
    XYZ*        m_a2;
};

3 个答案:

答案 0 :(得分:3)

import java.io.File; public class ReadXMLFile { public static void main(String argv[]) { try { File fXmlFile = new File("logs/file.xml"); DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance(); DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); Document doc = dBuilder.parse(fXmlFile); doc.getDocumentElement().normalize(); System.out.println("Main Tag:" + doc.getDocumentElement().getNodeName()); NodeList nList = doc.getElementsByTagName("SubTag"); for (int temp = 0; temp < nList.getLength(); temp++) { Node nNode = nList.item(temp); System.out.println("\nCurrent Element :" + nNode.getNodeName()); if (nNode.getNodeType() == Node.ELEMENT_NODE) { Element eElement = (Element) nNode; System.out.println("Data 1 : "+ eElement.getAttribute("ElementTagName1")); System.out.println("Data 2: "+ eElement.getElementsByTagName("ElementTagName2").item(0).getTextContent()); System.out.println("Data 2 : "+ eElement.getElementsByTagName("ElementTagName3") .item(0).getTextContent()); System.out.println("Data 4 : "+ eElement.getElementsByTagName("ElementTagName4").item(0).getTextContent()); System.out.println("Data 5 : "+ eElement.getElementsByTagName("ElementTagName5") .item(0).getTextContent()); } } } catch (Exception e) { e.printStackTrace(); }}} 成员函数中,所有非静态数据成员也被视为const,然后const变为m_a1const vector<XYZ>有一个const重载,因此在const std::vector::operator[]上执行operator[]您将得到一个const std::vector<XYZ>;其成员XYZ也变为xyz1;即const,它将衰减到const uint16_t [16],无法隐式转换为const uint16_t*

另一方面,对于const成员函数中类型为uint16_t*的数据成员m_a2,将成为XYZ*(注意它不是XYZ* const)。即指针本身是const XYZ*,但不是指针。然后使用const,它仍然会返回operator[],而不是const XYZ。这就是为什么它适用于以下声明。

答案 1 :(得分:1)

如果成员函数是const,则在该方法中访问的所有成员非mutable变量也被视为const,因此编译器不允许您创建非指针到const点到const成员数据。将您的代码更改为此

void getSomething() const
{
    const uint16_t* p = m_a1[0].xyz1; 
    // or simply
    // auto* p = m_a1[0].xyz1
}

在第二个中,指针本身是const,但不是它指向的数据。所以代替m_a2const XYZ*(这是一个指向const的指针),就像你想的那样,它的XYZ* const是一个const指针。

答案 2 :(得分:1)

不同之处在于,在第一个方法中,vector对象是const,因此只使用它的const方法,因此[]运算符返回一个const引用,而成员xyz1也是const。 / p>

在第二种方法中,指针m_a2是常量,但它指向的内存位置。这就是为什么在第二种情况下你不需要const。