`
lc52520
  • 浏览: 369308 次
  • 性别: Icon_minigender_1
  • 来自: 成都
社区版块
存档分类
最新评论

隐式类类型转换

阅读更多
C++ primer 中有这么一句话:可以用单个实参来调用的构造函数定义了从形参类型到该类型的一个隐式转换。

这么解释:

比如有个类A的对象a的成员函数的参数应该是类A的对象,但是把一个别的类型B的对象b传进去了,而且这个对象b的类型恰好是A的单参数构造函数参数类型,这时系统就用这个b自作聪明的创建了一个类A的临时对象c,虽然c和a都是A类型,但是是不同的对象。

这种隐式转换有很大风险,可以用explicit加在单参数构造函数前来避免这种类类隐形转换。

我个人认为这就是一种人为使用错误,而编译器又恰恰没有指出。

本来应该A.a(A(b)),凭什么用成A.a(b)?哈哈……



#include <string>

#include <iostream>

using namespace std;



class Fruit //定义一个类,名字叫Fruit

{

       string name;//定义一个name成员

       string colour;//定义一个colour成员

     

public:

       bool isSame(const Fruit& otherFruit)//期待的形参是另一个Fruit类对象,测试是否同名

       {

              return name == otherFruit.name;

       }

     

       void print()//定义一个输出名字的成员print()

       {

              cout << colour << "  " << name << endl;

       }

     

       Fruit(const string& nst, const string& cst = "green"):name(nst), colour(cst){}

       Fruit(){}

};



int main()

{

       Fruit apple("apple");

       Fruit orange("orange");



       cout << "apple = orange? : " << apple.isSame(orange) << endl;

       //隐式转换

       cout << "apple = \"apple\"? :" << apple.isSame(string("apple")) << endl;



       return 0;

}



你会发现最后的使用上,我们用一个string类型作一个期待Fruit类形参的函数的参数,结果竟然得出了是true(1),不要感到奇怪,这就是我现在要讲的东西,隐式类类型转换:“可以用单个实参来调用的构造函数定义了从形参类型到该类型的一个隐式转换。”(C++ Primer)

首先要单个实参,你可以把构造函数colour的默认实参去掉,也就是定义一个对象必须要两个参数的时候,文件编译不能通过。然后满足这个条件后,系统就知道怎么转换了,不过这里比较严格

以前我们构造对象的时候Fruit apple("apple")其实也已经有了一个转换,从const char *的C字符串格式,转为string,在这里,你再apple.isSame("apple")的话,蠢系统不懂得帮你转换两次,所以你必须要用 string()来先强制转换,然后系统才知道帮你从string隐式转换为Fruit,当然其实你自己也可以帮他完成。 cout<<"apple = \"apple\" ?:"<<apple.isSame(Fruit("apple"));这样。Fruit apple = Fruit("apple");  //定义一个Fruit类对象apple。也就是这样转换的。不过这就叫显式转换了,我们不标出来,系统帮我们完成的,叫隐式的呗。

这里要说的是,假如你显示转换就可以不管有多少参数了,比如在前面提到的必须需要两个参数的构造函数时的例子。



int main()

{

       Fruit apple("apple", "green");

       Fruit orange("orange", "yellow");



       cout << "apple = orange? : " << apple.isSame(orange) << endl;

       //显示转换

       cout << "apple = \"apple\"? :" << apple.isSame(Fruit("apple", "green")) << endl;



       return 0;

}



在你不想隐式转换,以防用户误操作怎么办?

C++提供了一种抑制构造函数隐式转换的办法,就是在构造函数前面加explicit关键字,你试试就知道,那时你再希望隐式转换就会导致编译失败,但是,要说明的是,显式转换还是可以进行,出于不提供错误源代码例子的原则,错误的情况就不提供了,自己试试吧



当一个类定义了一个有形参的构造函数后,在使用其他需要提供类对象的成员函数时,若没有在成员函数前如入强制显式转换,就可能发生在调用成员函数的时候提供一个有对应构造函数实参的对象,并由构造函数隐式的转换为一个临时类对象,并将临时对象传递给成员函数,当成员函数结束时,临时对象失效,造成错误.所以当不需要构造函数将其他对象隐式转换为类对象的时候,我们需要在构造函数前加上explicit进行限制,要求需要显式的使用构造函数转换其他对象为类对象.
  具体的例子如下:
  class Noname
  {
  public:
  Noname( );
  Noname(std::string & str1);
  bool Dosomething(Noname)
  {
  }
  private:
  std::string str;
  int ival;
  };
  此时调用Dosomething()时若传递一个string类的实参,编译器将自动调用Noname(std::string &str)创建一个临时对象并传递给Dosomething( );
  若在构造函数前加上explicit的话,就不能直接将string作为实参传递给Dosometing(),而需要显示的调用构造函数来创建对象并传递给Dosomething( ),如:Noname.Dosometing( Noname(str1))
分享到:
评论

相关推荐

    C++隐式类类型转换

    C++可以定义如何将其他类型的对象隐式转换为我们的类类型或将我们的类类型的对象隐式转换为其他类型。为了定义到类类型的隐式转换,需要定义合适的构造函数。  说明:可以用单个实参来调用的构造函数定义了从形参...

    C语言隐式类型转换规则

    ### C语言隐式类型转换规则详解 #### 一、引言 C语言作为一种广泛使用的编程语言,具有严格的类型检查机制。在C语言中,不同类型的数值可以通过类型转换来进行混合运算。这种转换分为两种:隐式类型转换和显式类型...

    《C++ Primer》隐式类类型转换学习整理

    隐式类类型转换是指在不显式调用构造函数的情况下,编译器自动进行的类型转换。这种转换经常出现在单个参数的构造函数中,使得一个类的对象可以被用来初始化或赋值给另一个类的对象。在《C++ Primer》一书中,作者...

    类的转换C++的内部数据类型遵循隐式类型转换规则

    但是,过度依赖或滥用隐式类型转换可能导致代码难以理解和维护,因此在设计类时应谨慎使用这些特性,确保转换的合理性和安全性。在实际编程中,应该清楚地了解转换的目的和可能的后果,以避免潜在的错误和意外行为。

    隐式类型转换

    "隐式类型转换" 隐式类型转换是C语言中的一种重要概念,它指的是在编译时由编译程序按照一定规则自动完成的数据类型转换。这种转换在C语言的表达式中经常出现,当不同类型的数据参与同一运算时,编译器就会按照规定...

    单元十:数据类型的隐式转换-数据类型的隐式转换完整版资料.pptx

    1. 隐式类型转换:这是最常见的一种隐式转换方式,编译器或解释器会自动将一种数据类型转换为另一种数据类型。 2. 显式类型转换:这是开发者主动地将一种数据类型转换为另一种数据类型。 隐式转换的优点: 1. 提高...

    C#显式类型与隐式转换

    在C#编程语言中,类型转换是非常重要的一个概念,它涉及数据类型的转换以及如何确保程序能够正确处理不同类型的数据。本文将基于提供的内容,详细介绍C#中几种常见的类型转换方法及其应用场景。 #### 1. 整型变量到...

    前端面试题之baseJS-==隐式类型转换.zip

    本文将详细探讨“前端面试题之baseJS-==隐式类型转换”这一主题,帮助你掌握JavaScript中的类型转换规则,以便在面试中能够自信地解答相关问题。 在JavaScript中,“==”双等号运算符用于比较两个值是否相等。然而...

    简单介绍JavaScript数据类型之隐式类型转换

    不同类型的变量比较要先转类型,叫做类型转换,类型转换也叫隐式转换。隐式转换通常发生在运算符加减乘除,等于,还有小于,大于等。。 typeof '11' //string typeof(11) //number '11' &lt; 4 //false 本章节单独...

    C++类各种类型转换_数据类型的相互转换_

    首先,我们讨论隐式类型转换(也称为自动类型转换)。在C++中,当一个数据类型可以安全地被转换为另一种类型时,编译器会自动执行这种转换。例如,较小的数据类型(如int)可以被赋值给较大的数据类型(如long long...

    c++隐式类型转换示例分享

    在C++编程语言中,隐式类型转换(Implicit Type Conversion)是一种编译器自动进行的数据类型转换,通常发生在不需要程序员明确指定的情况下。这种转换在某些操作中是允许的,但可能会导致意料之外的结果,因此需要...

    JavaScript隐式类型转换_.docx

    JavaScript中的隐式类型转换是其弱类型特性的重要体现,它允许不同数据类型的值在运算时进行自动转换,但这也可能导致一些意料之外的结果。在JavaScript中,数据类型包括字符串(String)、数字(Number)、布尔(Boolean...

    深入分析java中的类型转换

    在Java中,类型转换主要分为两大类:**隐式自动类型转换**和**强制手动类型转换**。 #### 隐式自动类型转换 隐式自动类型转换指的是Java编译器自动完成的类型转换过程。这种类型的转换通常发生在较小的数据类型向较...

    JS面试题大坑之隐式类型转换实例代码

    JavaScript中的隐式类型转换是开发者在编写代码时经常会遇到的一个陷阱,尤其在面试中,它经常作为考察开发者对语言理解深度的问题出现。本篇主要探讨的是JavaScript中的隐式类型转换,特别是那些容易出错的实例代码...

    MySQL隐式类型的转换陷阱和规则

    MySQL中的隐式类型转换是数据库操作中一个需要注意的重要概念,尤其在处理查询效率和优化时。隐式类型转换指的是在SQL语句中,当不同数据类型的值进行比较或运算时,MySQL会自动将其中一个或多个值转换为另一种类型...

    C++隐式类型转换运算符operator type()用法详解

    C++隐式类型转换运算符operator type()用法详解 C++隐式类型转换运算符operator type()是一种特殊的成员函数,用于实现类型转换的自动转换。这种运算符可以将一个类对象转换为其他类型,例如基本数据类型、自定义类...

    C_C++问题总结

    3.12 两种常用的实现隐式类类型转换的方式是什么?如何避免隐式类 型转换?3.13 STL中的vector:增减元素对迭代器的影响 3.14 STL中排序算法的实现 3.15 C和C++的区别 3.16 内存对齐 3.17 C++转换机制(static_cast...

Global site tag (gtag.js) - Google Analytics