c – 使用operator []的奇怪行为

前端之家收集整理的这篇文章主要介绍了c – 使用operator []的奇怪行为前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
花了最后几天尝试使用C操作符[]方法,我遇到了一个我无法解释的异常现象.下面的代码实现了一个简单的测试字符串类,它允许用户通过其下标“operator”方法访问单个字符.由于我想区分左值和右值下标上下文,“operator”方法返回自定义“CReference”类的实例,而不是标准的C字符引用.虽然“CReference”“operator char()”和“operator =(char)”方法似乎分别处理每个rvalue和lvalue上下文,但g拒绝编译而不存在额外的“operator =(CReference&)”方法,如记录如下.虽然添加方法似乎安抚了某种编译时依赖项,但在程序执行期间从未在运行时实际调用它.

作为一个认为他们已经对C复杂性有了基本了解的人,这个项目无疑已经证明是一种令人羞愧的经历.如果有人能够看到他们的方式来启发我在这里发生了什么,我会永远感激.与此同时,我将不得不拔出C书,以便在我所知道的和我认为知道的东西之间调和.

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

// Class for holding a reference to type char,retuned by the "operator[](int)"
// method of class "TestString". Independent methods permit differentiation
// between lvalue and rvalue contexts.
class CReference
{
 private:
   char& m_characterReference;

 public:
   // Construct CReference from char&
   CReference(char& m_initialiser)
     : m_characterReference(m_initialiser) {}

   // Invoked when object is referenced in a rvalue char context.
   operator char()
   {
    return m_characterReference;
   }

   // Invoked when object is referenced in a lvalue char= context.
   char operator=(char c)
   {
    m_characterReference = c;
    return c;
   }

   // NEVER INVOKED,but will not compile without! WHY???
   void operator=(CReference &p_assignator){}
};


// Simple string class which permits the manipulation of single characters
// via its "operator[](int)" method.
class TestString
{
 private:
   char m_content[23];

 public:
   // Construct string with test content.
   TestString()
   {
    strcpy(m_content,"This is a test object.");
   }

   // Return pointer to content.
   operator const char*()
   {
    m_content[22] = 0;
    return m_content;
   }

   // Return reference to indexed character.
   CReference operator[](int index)
   {
    return m_content[index];
   }
};


int main(int argc,char *argv[])
{
 TestString s1;

 // Test both lvalue and rvalue subscript access.
 s1[0] = s1[1]; 

 // Print test string.
 printf("%s\n",(const char*)s1);
 return 0;
}

解决方法

>行s1 [0] = s1 [1];如果您没有自己声明CReference,则会导致编译器为CReference生成隐式复制赋值运算符.这会导致错误,因为您的类具有无法复制的引用成员. >如果添加了一个带有const CReference&类型参数的赋值运算符,它将被赋值调用. >在您的代码中,您声明了一个类型为void operator =(CReference& p_assignator)的复制赋值运算符.这不能被调用,因为赋值的右侧是临时对象,不能绑定到非const引用.但是,声明此运算符的行为会导致编译器不尝试定义隐式复制赋值运算符,从而避免了先前的编译错误.由于无法调用此运算符,因此编译器会转到另一个带有char类型参数的赋值运算符.

猜你在找的C&C++相关文章