调用虚拟和非虚拟成员函数的开销相同......? [英] same overhead in calling virtual and non virtual member function...?

查看:75
本文介绍了调用虚拟和非虚拟成员函数的开销相同......?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Hello All,


到目前为止,我一直在阅读多态的类(具有

至少一个虚函数),虚拟函数调用get

在运行时解析,在此期间使用vtable指针使用

...


例如。

class one

{

virtual void fun1(){cout<<" one :: fun1" ;;} // This是一个虚拟的

函数。

void fun2(){cout<<" one :: fun2" ;;} //不是虚函数。


};


int main()

{

one * o = new one;

o-> fun1();

o-> fun2();

删除o;

o = NULL;

返回0;

}


所以当通过基类poitner调用虚函数时/>
这个电话实际上扩展到了这样的代码

o-> vfptr [0]();

我的困惑是如何调用非虚函数(这里有趣2

)在多态类中得到解决?

什么时候编译器决定调查vtable,什么时候不用?
看? br />
在这种情况下,我强烈地感觉到,每次编译器都有

来查看vtable而不管虚拟性或非虚拟性
函数。如果它在vtable中找到函数条目

然后它从那里调用函数,否则如果它没有找到任何

条目进入vtable它看起来对于非虚函数然后

执行函数代码?

所以换句话说,只要你的类是多态的,我们就得交易

总是这个开销是否类用户调用虚拟或

非虚函数...


任何人都可以澄清它吗??


谢谢和问候,

Yogesh Joshi

[见 http://www.gotw.ca/resources/clcm.htm 了解有关的信息]

[comp.lang.c ++。moderated。第一次海报:做到这一点! ]

解决方案

yp *********@indiatimes.com 写道:


所以换句话说,只要你的类是多态的,我们必须处理

这个开销总是无论班级用户是否调用虚拟或

非虚拟功能......


任何人都可以澄清一下..?



C ++标准没有指定vtable。但是对于大多数C ++

编译器实现,虚拟函数通过查看

解决vtable和非虚函数直接调用(就好像你是
称为非成员函数)无论该类是否为
多态。查看vtable的开销是

在现代CPU上是微不足道或无关紧要的,当然也不是什么东西

除非你有大量数据,否则你应该关心

(10 ^ 6的顺序 - 或许更多)小(16字节或更小)的对象

(我的观点 - 用谷物盐)。即使这样,我也可能保守过来。


使用非虚拟功能的主要原因是如果你想允许

编译器内联函数。编译器将有一个非常困难的时间(可能是不可能的)内置虚拟函数。


yp ********* @ indiatimes.com 写道:


大家好,


到目前为止,我已经阅读了多态的类(具有

至少一个虚函数) it),虚拟函数调用得到

在运行时解析,在此期间使用vtable指针

...


eg。

class one

{

virtual void fun1(){cout<<" one :: fun1" ;;} //这是一个虚拟的

函数。

void fun2(){cout<<" one :: fun2" ;;} //不是虚函数。< b / b

};


所以当通过基类poitner调用虚函数时

调用实际上会被扩展像这样的代码

o-> vfptr [0]();



是的,至少对于使用vtables实现虚拟

函数的C ++编译器。但一般的观点是,源代码中的一个函数调用虚拟

方法可以 - 在运行时 - 执行几个不同的方法中的任何一个(基于运行时类型)对象)每次都是

。所以调用虚方法需要运行时决定,这在调用非虚方法或

全局函数时是不需要的。


我的困惑是如何调用非虚函数(这里是fun2

)在多态类中得到解决?

什么时候编译器决定看看vtable什么时候不要看
看?



编译器生成lookup-code当被调用的方法已经被声明为虚拟时,否则它会生成对

方法的直接调用,该方法由对象的静态类型决定。


在这种情况下,我强烈地感觉到,每次编译器都有

来查看vtable,无论虚拟性如何或不是$

函数的虚拟性。如果它在vtable中找到函数条目

那么它会从那里调用函数,否则如果它没有找到任何

条目进入vtable它会查找非虚函数然后

执行函数代码?



运行时程序不需要确定方法是否是虚拟的
。编译器在编译时有这些信息 - 所以

只调用虚方法会产生虚拟

方法调用的开销。


所以换句话说,无论什么时候你的类都是多态的,我们不得不用这个开销来处理

,无论类用户是否调用虚拟或

非虚拟功能...



不,根本不是这样的。


Greg

[见 http://www.gotw.ca/resources/clcm。 htm 有关的信息]

[comp.lang.c ++。moderated。第一次海报:做到这一点! ]


< yp ********* @ indiatimes.comschrieb im Newsbeitrag

news:11 * *********************@i42g2000cwa.googlegr oups.com ...


Hello All,


到目前为止,我一直在读取多态类(具有至少一个虚拟函数的
),虚函数调用get

在运行时解决,在此期间使用vtable指针使用

..


例如。

class one

{

virtual void fun1(){cout<<" one :: fun1" ;;} //这是一个虚拟的

函数。

void fun2(){cout<<" one :: fun2" ;;} //不是虚函数。


};


int main()

{

one * o = new one;

o-> fun1();

o-> fun2();

删除o;

o = NULL;

返回0;

}


所以当虚函数通过基类poitner调用

调用实际上扩展到这样的代码

o-> vfptr [0]();

我的困惑是如何在多态类中解析对非虚函数的调用(这里是fun2

)?

什么时候编译器决定查看vtable什么时候不用?
看看?

在这种情况下我强烈地感觉到,每次编译器都有

来查看vtable无论虚拟性还是非虚拟的函数。如果它在vtable中找到函数条目

那么它会从那里调用函数,否则如果它没有在vtable中找到任何

条目它会查找非虚函数然后

执行函数代码?



您的编译器概念中有一个错误。编译器不会调用他们编译的

函数。他们生成代码来调用它们,而这个代码

除其他外依赖于函数firtuaity或非虚拟函数。

当编译器检测到对虚拟的调用时函数,它确实会发出一些代码来从vtable中获取函数的地址。但是如果要调用一个

非虚函数,编译器可以将地址

直接插入代码中。


此外,编译器不使用vtable和vtable。决定一个函数是否是虚拟的b $ b。通常编译器有更复杂的表,

还包含函数的名称,返回类型,

参数的数量和类型,以及许多其他数据。并且编译器必须在此表中查找每个标识符
。无论使用什么标识符。

实际上,编译器必须查找标识符以确定

标识符的用途。
< blockquote class =post_quotes>
所以换句话说,无论什么时候你的类都是多态的,我们必须用这个开销来处理

,无论类用户是否调用虚拟或

非虚函数...



在编译时,这可能是正确的,但更糟糕的是 - 即使一个类是

不是多态的,它仍然需要大约相同的时间来编译一个函数

调用。但是在运行时可能会有所不同。


HTH

Heinz

[见 http://www.gotw.ca/resources/clcm.htm 了解有关的信息/>
[comp.lang.c ++。moderated。第一次海报:做到这一点! ]


Hello All,

So far I have been reading that in case of a polymorphic class ( having
at least one virtual function in it), the virtual function call get
resolved at run time and during that the vtable pointer is made use
of..

eg.
class one
{
virtual void fun1(){ cout<<"one::fun1";} //This is a virtual
function.
void fun2(){ cout<<"one ::fun2";}//Not a virtual function.

};

int main()
{
one * o = new one;
o->fun1();
o->fun2();
delete o;
o= NULL;
return 0;
}

so when the virtual function gets called through the base class poitner
the call actually gets expanded to the code like this
o->vfptr[0]();
My confusion is how the call to the non virtual function (here fun2
)gets resolved in polymorphic class?
When does the compiler decide to look into the vtable and when not to
look?
As in this scenario I strongly feel that, every time the compiler has
to look into the vtable irrespective of the virtuality or non
virtuality of the function.If it finds the function entry in the vtable
then it calls the function from there otherwise if it doesn''t find any
entry into the vtable it looks for the non virtual function and then
execute the fuction code?
So in other words whenever your class is polymorphic , we have to deal
with this overhead always whether the class user calls the virtual or
non virtual function...

Can anyone please clarify it..?

Thanks and Regards,
Yogesh Joshi
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]

解决方案

yp*********@indiatimes.com wrote:

So in other words whenever your class is polymorphic , we have to deal
with this overhead always whether the class user calls the virtual or
non virtual function...

Can anyone please clarify it..?

The C++ standard does not specify a "vtable". However with most C++
compiler implementations, virtual functions are resolved by looking into
the vtable and non virtual functions are called directly (as if you
called a non-member function) regardless of whether the class is
polymorphic. The overhead of looking into the vtable is either
minuscule or irrelevant on modern day CPU''s and certainly not something
you should concern yourself with unless you will have large numbers
(order of 10^6 - perhaps more) of small (16 bytes or smaller) objects
(my opinion - take with grain-o-salt). Even then, I might be too
conservative.

The big reason for using a non-virtual function is if you want to allow
the compiler to inline the function. The compiler will have a very hard
time (possibly impossible) in-lining a the virtual function.


yp*********@indiatimes.com wrote:

Hello All,

So far I have been reading that in case of a polymorphic class ( having
at least one virtual function in it), the virtual function call get
resolved at run time and during that the vtable pointer is made use
of..

eg.
class one
{
virtual void fun1(){ cout<<"one::fun1";} //This is a virtual
function.
void fun2(){ cout<<"one ::fun2";}//Not a virtual function.

};

so when the virtual function gets called through the base class poitner
the call actually gets expanded to the code like this
o->vfptr[0]();

Yes, at least for C++ compilers that use vtables to implement virtual
functions. But the general point is that one function call to a virtual
method in the source code can - at runtime - execute any of several
distinct methods (based on the runtime type of the object) each and
every time. So calling a virtual method requires run-time
decision-making which is not needed when calling non-virtual methods or
global functions.

My confusion is how the call to the non virtual function (here fun2
)gets resolved in polymorphic class?
When does the compiler decide to look into the vtable and when not to
look?

The compiler generates "lookup-code" when the method being called has
been declared virtual, otherwise it generates a direct call to the
method as determined by the object''s static type.

As in this scenario I strongly feel that, every time the compiler has
to look into the vtable irrespective of the virtuality or non
virtuality of the function.If it finds the function entry in the vtable
then it calls the function from there otherwise if it doesn''t find any
entry into the vtable it looks for the non virtual function and then
execute the fuction code?

The program at runtime does not need to determine whether a method is
virtual or not. The compiler has that information at compile time - so
only calls to virtual methods will have the overhead of a virtual
method call.

So in other words whenever your class is polymorphic , we have to deal
with this overhead always whether the class user calls the virtual or
non virtual function...

No, that is not the case at all.

Greg
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]


<yp*********@indiatimes.comschrieb im Newsbeitrag
news:11**********************@i42g2000cwa.googlegr oups.com...

Hello All,

So far I have been reading that in case of a polymorphic class ( having
at least one virtual function in it), the virtual function call get
resolved at run time and during that the vtable pointer is made use
of..

eg.
class one
{
virtual void fun1(){ cout<<"one::fun1";} //This is a virtual
function.
void fun2(){ cout<<"one ::fun2";}//Not a virtual function.

};

int main()
{
one * o = new one;
o->fun1();
o->fun2();
delete o;
o= NULL;
return 0;
}

so when the virtual function gets called through the base class poitner
the call actually gets expanded to the code like this
o->vfptr[0]();
My confusion is how the call to the non virtual function (here fun2
)gets resolved in polymorphic class?
When does the compiler decide to look into the vtable and when not to
look?
As in this scenario I strongly feel that, every time the compiler has
to look into the vtable irrespective of the virtuality or non
virtuality of the function.If it finds the function entry in the vtable
then it calls the function from there otherwise if it doesn''t find any
entry into the vtable it looks for the non virtual function and then
execute the fuction code?

There is one error in your Concept of a compiler. Compilers don''t call the
functions they compile. They generate code to call them, and this code
depends on, among other things, a functions firtuaity or non- virtually.
When the compiler detects a call to a virtual function, it may indeed emit
some code to fetch the function''s address from a "vtable". But if a
non-virtual function should be called, the compiler can insert the address
directly into the code.

Also, the compiler does not use a "vtable" to decide whether a function is
virtual or not. Usually compilers have much more complicated tables, which
also contain a function''s name, its return type, number and type of its
parameters, and perhaps many other data. And the compiler has to look-up
each identifier in this table. No matter what that identifier is used for.
Actually, the compiler has to look-up the identifier to determine what the
identifier is used for.

So in other words whenever your class is polymorphic , we have to deal
with this overhead always whether the class user calls the virtual or
non virtual function...

At compile-time, that might be correct but even worse -- even if a class is
not polymorphic, it still takes about the same time to compile a function
call. But there might be a difference at run-time.

HTH
Heinz
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]


这篇关于调用虚拟和非虚拟成员函数的开销相同......?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆