c++类成员访问只看静态类型

cpp 复制代码
struct Base { int b; };
struct Derived : Base { int d; };

Derived dv;
Base* pb = &dv;
Derived* pd = static_cast<Derived*>(pb);

pb 不能访问变量 d ,pb->b 可以,访问 b 可以

cpp 复制代码
pb->b = 1;   // OK,改的就是 dv.b
pb->d = 2;   // 编译错误:'struct Base' has no member named 'd'

原因很简单:成员访问只看静态类型 。pb 的静态类型是 Base*,编译器只认 Base 里声明的成员,而 Base 只有 b。运行时的实际类型是 Derived 这一点,对普通数据成员访问没有任何影响。

几点补充

  1. pb->b 和 dv.b 访问的是同一块内存(Base 子对象),互相可见:

    cpp 复制代码
    pb->b = 1;
    assert(dv.b == 1);
  2. 想通过 pb 访问 d,必须先做转换 ,把静态类型改回 Derived*:

    cpp 复制代码
    static_cast<Derived*>(pb)->d = 2;  // 前提:pb 确实指向 Derived 对象
  3. 虚函数是唯一的"例外" :如果 Base 有虚函数,pb->f() 会按对象的动态类型分派到 Derived::f()。但数据成员没有虚机制,不存在"虚成员变量",所以 pb->d 永远不会合法。

  4. 换成 Base b; Base* p = &b; 也一样 :p->b 合法,p->d 编译不过。区别只在于,此时即使强转成 Derived* 再访问 d 也是 UB ,因为对象本身不是 Derived。

相关推荐
starzy19905 分钟前
深入理解Scala嵌套函数:作用域封装之道
开发语言·scala
Sakura_j_h_15 分钟前
从零写一个 MCP stdio Server:用 Python 校验博客文章格式
开发语言·python·自动化·ai工具·mcp·json-rpc
青少儿编程课堂2 小时前
蓝桥杯青少组图形化 STEMA 省考(报名倒计时·11/22开考)+ 全国青少年信息素养大赛 2026—2027赛季 + 电子学会图形化考级:校园华容道大闯关
c++·python·算法·bfs·信息学竞赛
白杨尚青2 小时前
C++进阶篇(五):红黑树——四条规则、三种插入情况与旋转变色
开发语言·数据结构·c++·stl·红黑树·平衡二叉树
.道阻且长.2 小时前
Linux基本开发工具:gdb和cgdb的使用
linux·运维·服务器·开发语言
starzy19903 小时前
深入理解Scala匿名函数:函数式编程基石
开发语言·scala
旖旎夜光3 小时前
【C++ 基础入门】C++ 继承(上):概念、切片、隐藏、默认成员函数与友元
c++·笔记·学习
apcipot_rain3 小时前
C++转Java日记(05)
java·开发语言·c++
apcipot_rain12 小时前
C++转Java日记(04)
java·开发语言·c++
云和数据.ChenGuang14 小时前
LangGraph 异步 Node 的设计与写法实践
开发语言·人工智能·python·机器学习·php