访问空指针问题

小蒙子 2014-01-09 09:19:16
之前由于自己的粗心,声明了一个类的指针对象后,赋值为NULL,然后忘记分配内存给它就直接使用了。
class A
{
void test()
{
printf("test A");
}
};
void main()
{
A *a=NULL;
a->test();
}
我使用时就类似上面的才操作,test中没有对A的成员变量的访问,这样不会出现编译错误,调试也没问题。
我的实际的程序中调用的成员函数,它没有使用A的成员变量,但是有局部变量
我的问题就是这种情况下,时间久了会导致程序死掉吗?我没有在test中访问成员变量哦。
哪位大神帮我解答一下,谢谢
...全文
670 34 打赏 收藏 转发到动态 举报
写回复
用AI写文章
34 条回复
切换为时间正序
请发表友善的回复…
发表回复
cc509a 2016-01-20
  • 打赏
  • 举报
回复
要是换成virtual就回崩溃,因为指向null的指针找不到对应的虚表。楼主的写法就是静态绑定,他们的静态代码只有一套,是通用的,但是楼主要访问自己成员变量就会crash,因为非静态成员变量是每个对象一份
zhllxt 2014-01-10
  • 打赏
  • 举报
回复
引用 32 楼 unituniverse2 的回复:


class A
{
public:
	virtual void test()
	{
		printf("test A");
	}
};

int main(void)
{
	A *a=NULL;

	a->test();
	return 0;
}
楼主贴的代码,估计他本人都没试过,因为[此处省略2万字]。 你们不要上当了
这么简单的代码,30秒就测试完了,为何不测试一下试试再如是说呢。
unituniverse2 2014-01-10
  • 打赏
  • 举报
回复


class A
{
public:
	virtual void test()
	{
		printf("test A");
	}
};

int main(void)
{
	A *a=NULL;

	a->test();
	return 0;
}
楼主贴的代码,估计他本人都没试过,因为[此处省略2万字]。 你们不要上当了
unituniverse2 2014-01-10
  • 打赏
  • 举报
回复
要不楼主再试试这个??

class A
{
virtual void test()
{
printf("test A");
}
};
void main()
{
A *a=NULL;
a->test();
}
zhllxt 2014-01-09
  • 打赏
  • 举报
回复
经过测试发现 A *a=NULL; a->test(); 的确不报错,可以正常运行。
Stone-hdj 2014-01-09
  • 打赏
  • 举报
回复
学习了,但是我有个疑问 a->test();a是空指针,这样也能调用test?
iwong 2014-01-09
  • 打赏
  • 举报
回复
空指针访问成员函数,如果函数中未访问this指针(数据成员),确实是没问题的。而且有时可以当作一种编码技巧。
漫步者、 2014-01-09
  • 打赏
  • 举报
回复
引用 23 楼 u011385123 的回复:
[quote=引用 20 楼 ganpengjin1 的回复:] [quote=引用 17 楼 u011385123 的回复:] [quote=引用 14 楼 ganpengjin1 的回复:] [quote=引用 13 楼 ganpengjin1 的回复:] [quote=引用 12 楼 u011385123 的回复:] [quote=引用 9 楼 starytx 的回复:] 你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。[/quote] 跟编译器没有关系,它的成员方法不占内存空间的,所以你可以直接去调用它(前提是你的ptr不能为野指针,否则会崩掉),但是如果你的空指针去调用一个有内存空间的数据成员的话,这个时候就会崩掉,一个空指针没有有权限去调用一个有内存大小的数据对象。[/quote] 编译器编译后的成员函数的第一个参数是this指针,通过this指针引用数据成员及调用其它成员函数。 由于你调用的成员函数没有使用到类的数据成员,所以即使传入的this指针为空,运行也不会出错。 [/quote] 也就是说调用其它成员函数也会吗?我用的这个成员函数中虽然没有引用成员变量,但是调用了其它的成员函数,不过这个成员函数中也没有引用成员变量。我的程序为什么隔了那么久才死掉,让我很纳闷。[/quote] 你调用的成员函数,都不会出问题,即使this为0也不会,因为不需要用到this来调用它,根据标准来说,这个应该是属于未定义行为的。[/quote] 也就说我这种做法不知道什么时候就出现什么不知道的问题了,也可能很久都没问题。 作为一个女程序猿,表示压力很大,学习了。O(∩_∩)O谢谢,结贴。[/quote] 对呀,所以说,应该按照规范来写程序,不然那一天忽然出错了,到处debug就麻烦了。
小蒙子 2014-01-09
  • 打赏
  • 举报
回复
引用 20 楼 ganpengjin1 的回复:
[quote=引用 17 楼 u011385123 的回复:] [quote=引用 14 楼 ganpengjin1 的回复:] [quote=引用 13 楼 ganpengjin1 的回复:] [quote=引用 12 楼 u011385123 的回复:] [quote=引用 9 楼 starytx 的回复:] 你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。[/quote] 跟编译器没有关系,它的成员方法不占内存空间的,所以你可以直接去调用它(前提是你的ptr不能为野指针,否则会崩掉),但是如果你的空指针去调用一个有内存空间的数据成员的话,这个时候就会崩掉,一个空指针没有有权限去调用一个有内存大小的数据对象。[/quote] 编译器编译后的成员函数的第一个参数是this指针,通过this指针引用数据成员及调用其它成员函数。 由于你调用的成员函数没有使用到类的数据成员,所以即使传入的this指针为空,运行也不会出错。 [/quote] 也就是说调用其它成员函数也会吗?我用的这个成员函数中虽然没有引用成员变量,但是调用了其它的成员函数,不过这个成员函数中也没有引用成员变量。我的程序为什么隔了那么久才死掉,让我很纳闷。[/quote] 你调用的成员函数,都不会出问题,即使this为0也不会,因为不需要用到this来调用它,根据标准来说,这个应该是属于未定义行为的。[/quote] 也就说我这种做法不知道什么时候就出现什么不知道的问题了,也可能很久都没问题。 作为一个女程序猿,表示压力很大,学习了。O(∩_∩)O谢谢,结贴。
i_Seven_ 2014-01-09
  • 打赏
  • 举报
回复
test方法要加public访问控制符,要不然默认是private访问的
漫步者、 2014-01-09
  • 打赏
  • 举报
回复
引用 19 楼 u011385123 的回复:
[quote=引用 16 楼 zhuobattle 的回复:] 另外你这个函数本身不是virtual函数吧?
不是virtual的[/quote] 与virtual 无关,不需要考虑这个问题。
漫步者、 2014-01-09
  • 打赏
  • 举报
回复
引用 17 楼 u011385123 的回复:
[quote=引用 14 楼 ganpengjin1 的回复:] [quote=引用 13 楼 ganpengjin1 的回复:] [quote=引用 12 楼 u011385123 的回复:] [quote=引用 9 楼 starytx 的回复:] 你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。[/quote] 跟编译器没有关系,它的成员方法不占内存空间的,所以你可以直接去调用它(前提是你的ptr不能为野指针,否则会崩掉),但是如果你的空指针去调用一个有内存空间的数据成员的话,这个时候就会崩掉,一个空指针没有有权限去调用一个有内存大小的数据对象。[/quote] 编译器编译后的成员函数的第一个参数是this指针,通过this指针引用数据成员及调用其它成员函数。 由于你调用的成员函数没有使用到类的数据成员,所以即使传入的this指针为空,运行也不会出错。 [/quote] 也就是说调用其它成员函数也会吗?我用的这个成员函数中虽然没有引用成员变量,但是调用了其它的成员函数,不过这个成员函数中也没有引用成员变量。我的程序为什么隔了那么久才死掉,让我很纳闷。[/quote] 你调用的成员函数,都不会出问题,即使this为0也不会,因为不需要用到this来调用它,根据标准来说,这个应该是属于未定义行为的。
小蒙子 2014-01-09
  • 打赏
  • 举报
回复
引用 16 楼 zhuobattle 的回复:
另外你这个函数本身不是virtual函数吧?
不是virtual的
FrankHB1989 2014-01-09
  • 打赏
  • 举报
回复
UB。不崩是实现的权利,崩了是LZ活该。
小蒙子 2014-01-09
  • 打赏
  • 举报
回复
引用 14 楼 ganpengjin1 的回复:
[quote=引用 13 楼 ganpengjin1 的回复:] [quote=引用 12 楼 u011385123 的回复:] [quote=引用 9 楼 starytx 的回复:] 你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。[/quote] 跟编译器没有关系,它的成员方法不占内存空间的,所以你可以直接去调用它(前提是你的ptr不能为野指针,否则会崩掉),但是如果你的空指针去调用一个有内存空间的数据成员的话,这个时候就会崩掉,一个空指针没有有权限去调用一个有内存大小的数据对象。[/quote] 编译器编译后的成员函数的第一个参数是this指针,通过this指针引用数据成员及调用其它成员函数。 由于你调用的成员函数没有使用到类的数据成员,所以即使传入的this指针为空,运行也不会出错。 [/quote] 也就是说调用其它成员函数也会吗?我用的这个成员函数中虽然没有引用成员变量,但是调用了其它的成员函数,不过这个成员函数中也没有引用成员变量。我的程序为什么隔了那么久才死掉,让我很纳闷。
zhuobattle 2014-01-09
  • 打赏
  • 举报
回复
另外你这个函数本身不是virtual函数吧?
zhuobattle 2014-01-09
  • 打赏
  • 举报
回复
引用 10 楼 u011385123 的回复:
[quote=引用 8 楼 zhuobattle 的回复:] [quote=引用 5 楼 u011385123 的回复:] [quote=引用 3 楼 ganpengjin1 的回复:] 确定没有崩掉吗?一般都是会直接死掉的
没有死掉,因为没有操作成员变量,运行了有一个多月吧才死掉,我看日志定位到这里,虽然它有错,但是不确定是不是这个问题导致的,想重现又一直重现不了。[/quote] 只是说程序逻辑分支可能极少情况下会执行到这里[/quote] 这个地方每天执行24次,1个小时1次,但是我把时间缩小了3秒执行1次,跑了1天也没有重现,难道是很偶然才会发生? 我看到网上有的人说:因为成员函数的调用其实和普通函数差不多,编译器只不过自动多加了一个this指针的参数而已,this指针这个时候为空,如果函数内部没有利用这个this指针存取成员变量,这样操作就是安全的。[/quote] 你的说法有一定道理,建议你可以看下编译后的汇编代码,因为像这样的调用,release优化后压根不会去执行函数调用开销,直接把test里的功能在当前函数展开了。 DEBUG确实是没用到ecx指针
漫步者、 2014-01-09
  • 打赏
  • 举报
回复
引用 13 楼 ganpengjin1 的回复:
[quote=引用 12 楼 u011385123 的回复:] [quote=引用 9 楼 starytx 的回复:] 你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。[/quote] 跟编译器没有关系,它的成员方法不占内存空间的,所以你可以直接去调用它(前提是你的ptr不能为野指针,否则会崩掉),但是如果你的空指针去调用一个有内存空间的数据成员的话,这个时候就会崩掉,一个空指针没有有权限去调用一个有内存大小的数据对象。[/quote] 编译器编译后的成员函数的第一个参数是this指针,通过this指针引用数据成员及调用其它成员函数。 由于你调用的成员函数没有使用到类的数据成员,所以即使传入的this指针为空,运行也不会出错。
漫步者、 2014-01-09
  • 打赏
  • 举报
回复
引用 12 楼 u011385123 的回复:
[quote=引用 9 楼 starytx 的回复:] 你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。[/quote] 跟编译器没有关系,它的成员方法不占内存空间的,所以你可以直接去调用它(前提是你的ptr不能为野指针,否则会崩掉),但是如果你的空指针去调用一个有内存空间的数据成员的话,这个时候就会崩掉,一个空指针没有有权限去调用一个有内存大小的数据对象。
小蒙子 2014-01-09
  • 打赏
  • 举报
回复
引用 9 楼 starytx 的回复:
你为什么要考研编译器?
我都要哭了,都说是粗心了,麻烦大家帮我解答一下这个问题,别在纠结我和编译器的关系了,我也知道我对不起编译器。我只想弄明白为什么程序能正常运行,过了很久才死掉是不是很大可能性与这个有关。我有疑问是因为10L我说的那样,我在这个函数中并没有对成员变量做操作。
加载更多回复(14)

64,647

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧