精华内容
下载资源
问答
  • 由于类成员初始化总在构造函数执行之前 1)从必要性:  a. 成员是类或结构,且构造函数带参数:成员初始化时无法调用缺省(无参)构造函数  b. 成员是常量或引用:成员无法赋值,只能被初始化 2)从效率上: ...

    先总结下:

    由于类成员初始化总在构造函数执行之前

    1)从必要性:

         a. 成员是类或结构,且构造函数带参数:成员初始化时无法调用缺省(无参)构造函数

         b. 成员是常量或引用:成员无法赋值,只能被初始化

    2)从效率上:

        如果在类构造函数里赋值:在成员初始化时会调用一次其默认的构造函数,在类构造函数里又会调用一次成员的构造函数再赋值

        如果在类构造函数使用初始化列表:仅在初始化列表里调用一次成员的构造函数并赋值


    -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

    以下内容参考自 c++中构造函数初始化的方法以及主要区别

    ----------------------

    一、我的问题是关于初始化C++类成员的。我见过许多这样的代码: 

    CSomeClass::CSomeClass() 
    { 
    	x=0; 
    	y=1; 
    } 
    而在别的什么地方则写成下面的样子: 
    CSomeClass::CSomeClass() : x(0), y(1) 
    { 
    
    } 

    我的一些程序员朋友说第二种方法比较好,但他们都不知道为什么是这样。你能告诉我这两种类成员初始化方法的区别吗? 

    回答 

    从技术上说,你的程序员朋友是对的,但是在大多数情况下,两者实际上没有区别。有两个原因使得我们选择第二种语法,它被称为成员初始化列表:一个原因是必 须的,另一个只是出于效率考虑。 

    让我们先看一下第一个原因——必要性。设想你有一个类成员,它本身是一个类或者结构,而且只有一个带一个参数的构造函数。 
    class CMember { 
    public: 
    
    CMember(int x) { ... } 
    
    }; 

    因为Cmember有一个显式声明的构造函数,编译器不产生一个缺省构造函数(不带参数),所以没有一个整数就无法创建Cmember的一个实例。 
    CMember* pm = new CMember; // Error!! 
    CMember* pm = new CMember(2); // OK 

    如果Cmember是另一个类的成员,你怎样初始化它呢?你必须使用成员初始化列表。 
    class CMyClass { 
    CMember m_member; 
    
    public: 
    
    CMyClass(); 
    
    }; 
    
    //必须使用成员初始化列表 
    CMyClass::CMyClass() : m_member(2) 
    { 
    ...
    } 
    

    没有其它办法将参数传递给m_member,如果成员是一个常量对象或者引用也是一样。根据C++的规则,常量对象和引用不能被赋值,它们只能被初始化。 

    第二个原因是出于效率考虑,当成员类具有一个缺省的构造函数和一个赋值操作符时。MFC的Cstring提供了一个完美的例子。假定你有一个类 CmyClass具有一个Cstring类型的成员m_str,你想把它初始化为 "yada yada. "。你有两种选择: 
    CMyClass::CMyClass() { 
    // 使用赋值操作符 
    // CString::operator=(LPCTSTR); 
    m_str = _T( "yada yada "); 
    
    } 
    //使用类成员列表 
    // and constructor CString::CString(LPCTSTR) 
    CMyClass::CMyClass() : m_str(_T( "yada yada ")) 
    { 
    
    } 

    在 它们之间有什么不同吗?是的。编译器总是确保所有成员对象在构造函数体执行之前初始化,因此在第一个例子中编译的代码将调用CString:: Cstring来初始化m_str,这在控制到达赋值语句前完成。在第二个例子中编译器产生一个对CString:: CString(LPCTSTR)的调用并将 "yada yada "传递给这个函数。结果是在第一个例子中调用了两个Cstring函数(构造函数和赋值操作符),而在第二个例子中只调用了一个函数。在 Cstring的例子里这是无所谓的,因为缺省构造函数是内联的,Cstring只是在需要时为字符串分配内存(即,当你实际赋值时)。但是,一般而言, 重复的函数调用是浪费资源的,尤其是当构造函数和赋值操作符分配内存的时候。在一些大的类里面,你可能拥有一个构造函数和一个赋值操作符都要调用同一个负 责分配大量内存空间的Init函数。在这种情况下,你必须使用初始化列表,以避免不要的分配两次内存。在内部类型如ints或者longs或者其它没有构 造函数的类型下,在初始化列表和在构造函数体内赋值这两种方法没有性能上的差别。不管用那一种方法,都只会有一次赋值发生。有些程序员说你应该总是用初始 化列表以保持良好习惯,但我从没有发现根据需要在这两种方法之间转换有什么困难。在编程风格上,我倾向于在主体中使用赋值,因为有更多的空间用来格式化和 添加注释,你可以写出这样的语句:x=y=z=0; 

    或者memset(this,0,sizeof(this)); 

    注意第二个片断绝对是非面向对象的。 

    当我考虑初始化列表的问题时,有一个奇怪的特性我应该警告你,它是关于C++初始化类成员的,它们是按照声 明的顺序初始化的,而不是按照出现在初始化列表中的顺序。 
    class CMyClass { 
    CMyClass(int x, int y); 
    int m_x; 
    int m_y; 
    }; 
    
    CMyClass::CMyClass(int i) : m_y(i), m_x(m_y) 
    { 
    
    } 

    你 可能以为上面的代码将会首先做m_y=I,然后做m_x=m_y,最后它们有相同的值。但是编译器先初始化m_x,然后是m_y,,因为它们是按这样的顺 序声明的。结果是m_x将有一个不可预测的值。我的例子设计来说明这一点,然而这种bug会更加自然的出现。有两种方法避免它,一个是总是按照你希望它们 被初始化的顺序声明成员,第二个是,如果你决定使用初始化列表,总是按照它们声明的顺序罗列这些成员。这将有助于消除混淆。

    二、很多的人对中构造函数寝初始化很多的困惑,对冒号后初始化不是太明白,总搞不清楚它们之间的区别,我想把我对这个问题的理解和看法和大家讨论讨 论。 

    在程序中定义变量并初始化的机制中,有两种形式,一个是我们传统的初始化的形式,即赋值运算符赋值,还有一种是括号赋值,如: 
    int a=10; 
    char b='r';\\赋值运算符赋值 
    int a(10);\ 
    char b('r');\\括号赋值 
    以上定义并初始化的形式是正确的,可以通过编译,但括号赋值只能在变量定义并初始化中,不能用在变量定义后再赋值,这是和赋值运算符赋值的不同之处,如: 
    (1) 
    int a; \\先定义一个变量 
    ...... 
    a=10; \\根据需要赋值 

    (2) 
    int b; \\先定义一个变量 
    ...... 
    b(10); \\和(1)一样根据需要赋值 
    (1)是可以用通过编译,定义一个变量a但并没有初始化,在需要变量a的时候,通过赋值运算符把10赋给a,而在(2)中,是通过括号把10赋值给b,但 编译系统认为 
    这是一个函数的调用,函数名为b,10为实际参数,所以编译错误。因此,括号赋值只用在定义变量并初始化中。



    现在我们来看构造函数中冒号初始化和函数初始化的问题,类构造函数的作用是创建一个类的对象时,调用它来构造这个类对象的数据成员,一要给出此数据成员分 配内存空间,二是要给函数数据成员初始化,构造数据成员是按数据成员在类中声明的顺序进行构造。 

    冒号初始化与函数体初始化的区别在于: 

    冒号初始化是给数据成员分配内存空间时就进行初始化,就是说分配一个数据成员只要冒号后有此数据成员的赋值表达式(此表达式必须是括号赋值表达式),那么 分配了内存空间后在进入函数体之前给数据成员赋值,就是说初始化这个数据成员此时函数体还未执行。 

    对于在函数中初始化,是在所有的数据成员被分配内存空间后才进行的。 

    这样是有好处的,有的数据成员需要在构造函数调入之后函数体执行之前就进行初始化如引用数据成员,常量数据成员和对象数据成员,看下面的一段程序: 

    class student 
    {public : 
    student () 
    . 
    . 
    . 
    protected: 
    const int a; 
    int &b;
    } 
    
    student ::student (int i,int j) 
    { 
    a=i; 
    b=j; 
    } 

    在Student类中有两个数据成员,一个是常量数据成员,一个是引用数据成员,并且在构造函数中初始化了这两个数据成员,但是这并不能通过编译,因为常 量初始化时必须赋值,它的值是不能再改变的,与常量一样引用初始化也需要赋值,定义了引用后,它就和引用的目标维系在了一起,也是不能再被赋值的。所以C 
    ++":"后初始化的机制,使引用和常量数据成员变为可能的,Student类的构造函数应为: 
    student ::student(int i,int j):a(i),b(j){} 

    在下面的程序: 
    class teach 
    { 
    public : 
    teach(char *p="name",int a=0) 
    . 
    . 
    . 
    protected: 
    char name[30]; 
    int age; 
    } 
    teach ::teach(char*p,int a) 
    { 
    strcopy(name ,p); 
    age=a; 
    cout>>name>>endl; 
    } 
    class student 
    { 
    public: 
    student (char *p="name"); 
    . 
    . 
    . 
    protected; 
    char name[30]; 
    teach teacher; 
    }; 
    student::student(char *p) 
    { 
    strcopy(name,p); 
    cont>>name>>endl; 
    } 

    在上面的程序中通不过编译,编译系统会告诉你teacher这个类对象缺默认构造函数,因为在teach 类中没有定义默认的构造函数。那么带参数的构造函数怎么进行构造呢?通过我们前面提到的冒号赋值。那它的构造函数应该是: 
    student::student(char *p,char *pl,int ag):teacher(pl,ag) 
    { 
    strcopy(name,p); 
    cont>>name>>endl; 
    } 

    就是说在没有默认构造函数的时候,如果一个类对象是另一个类的数据成员,那么初始化这个数 据成员,就应该放到冒号后面。这样可以带参数。在类的定义中,如: 
    protected; 
    char name[30]; 
    teach teacher 
    类对象是不能带参数的,因为它只是声明。 
    展开全文
  • 在bootstrap table 初始化中 在columns中能不能对返回的数据进行截取字符串? 能不能用foreach循环啊
  • 初始化中OnCreate与OnResume的区别

    千次阅读 2016-02-24 09:32:08
    有人说说 oncreate 里面初始化不变的控件, onresume 里面初始化变的控件,这个也许你执行没有问题,但是这么想的时候已经错了。因为 oncreate 就代表了初始化。 所以所有的控件都要在 oncreate 里面初始化。...
    	这和生命周期没有关系。 因为如果这个 activity 是最终的叶子节点,那么放哪里都可以。
    	oncreate 和 onresume 在第一次创建的时候都会执行。但是实际上 oncreate 和 onresume 的确有区别。
    	oncreate 是当被创建的时候执行, onresume 是被展示的时候执行。比如在栈式管理的方式下,如果不被销毁,那么oncreate 只会被执行一次, 而 onresume是依照展示机会执行。有人说说 oncreate 里面初始化不变的控件, onresume 里面初始化变的控件,这个也许你执行没有问题,但是这么想的时候已经错了。因为 oncreate 就代表了初始化。 所以所有的控件都要在 oncreate 里面初始化。onresume 里面去执行初始化后被展示的时候要进行的行为操作。
    
    
    http://www.cnblogs.com/shaocm/archive/2012/11/30/2796105.html
    
    展开全文
  • 初始化列表中初始化数组

    千次阅读 2019-03-23 14:28:54
    学习了一下前缀树。 需要用到一个结构体保存两个指针,如下 struct Node ...能不能将初始化操作放在初始化列表呢,如下 以上两种写法都有问题,突然想到,数组应该用大括号初始化啊 就酱。 ...

    学习了一下前缀树。

    需要用到一个结构体保存两个指针,如下

    struct Node
    {
    	Node()
    	{
    		nexts[0] = nullptr;
    		nexts[1] = nullptr;
    	}
    	Node *nexts[2];
    };

    能不能将初始化操作放在初始化列表中呢,如下

     以上两种写法都有问题,突然想到,数组应该用大括号初始化啊 

     就酱。

    展开全文
  • 常用的初始化方法有四种,分别是高斯初始化、Xavier初始化和MSRA初始化。它们一般都把偏置初始化为0,但对权值进行随机初始化。其中,高斯初始化比较容易理解,就是根据某个高斯分布来初始化权值,但均值通常选0,...

    在训练神经网络之前,必须对其全值和偏置进行初始化。常用的初始化方法有四种,分别是高斯初始化、Xavier初始化和MSRA初始化。它们一般都把偏置初始化为0,但对权值进行随机初始化。其中,高斯初始化比较容易理解,就是根据某个高斯分布来初始化权值,但均值通常选0,方差需要按经验人工选择。下面对Xavier和MSRA以及He做进一步的说明。

    Xavier的基本思想是保持信息在神经网络中流动过程的方差不变。假设激活函数是关于0点对称的,且主要针对于全连接神经网络,适应于tanh和softsign。这种方法在实际应用时根据一个均匀分布来初始化权值。如果某个神经元y_jn 个输入 x_1,x_2,...,x_n ,相应的连接权值为 w_{ij} ,则满足关系:

    y_j = w_{1j}x_1+w_2jx_2+...+w_{nj}x_n +b

    那么采用Xavier进行初始化的方法就是:

    w_{ij}\sim U[-\frac{sqrt(6)}{sqrt(n_i+n_i+1)},\frac{sqrt(6)}{sqrt(n_i+n_i+1)}],b=0

    MSRA的基本思想与Xavier类似,但主要是针对ReLU和PReLU激活函数来设计的。这种方法在实际应用时根据一个方差为\delta =sqrt(2/n) 的零均匀高斯分布来初始化权值,即

    w_{ij} \sim N(0,\frac{2}{n}), b=0

    He的基本思想是正向传播时,状态值的方差保持不变;反向传播时,关于激活值的梯度的方差保持不变。

    适用于ReLU的初始化方法:

    w_{ij} \sim N(0,sqrt(\frac{2}{n_i})), b=0

    适用于Leakly ReLU的初始化方法:

    w_{ij} \sim N(0,sqrt(\frac{2}{(1+\alpha^2)n_i})), b=0

    在darknet中CNN的权值初始化采用He的方法,具体实现见源码。后续我们会在【darknet源码解析】系列中详细讲解其实现。

    完,

    展开全文
  • Java的静态初始化和非静态初始化

    千次阅读 2017-01-09 19:03:30
    Java的静态初始化和非静态初始化
  • C++的值初始化和默认初始化

    千次阅读 多人点赞 2018-10-31 21:33:08
    1、值初始化 顾名思义,就是用数值初始化变量。如果没有给定一个初始值,就会根据变量或类对象的类型提供一个初始值。对于int类型其值初始化后的值为0。 2、默认初始化:如果定义变量时没有指定初值,则变量被...
  • 最近写c语言的结构体遇到了些问题,从网上找了些资料如下: 结构体是连续存储的,但由于结构体成员类型各异,所以会存在内存对齐问题,也就是内存里面会有空档,...结构体是可以直接初始化的,在定义的时候,就可
  • JAVA数组的初始化

    万次阅读 2019-05-31 14:12:51
    数组的初始化常见的两种方法 1.静态初始化 2.动态初始化 格式: 1.动态初始化格式: 数据类型 [ ] 数组名称 = new 数据类型[数组长度] 2.静态初始化格式: 数据类型 [ ] 数组名称 = new 数据类型[ ]{元素1,元素2,...
  • C++ 结构体初始化与赋值

    万次阅读 多人点赞 2016-05-30 13:28:57
    1.CC++结构体的初始化今天看到项目对自定义结构体初始化方式有点陌生,特在此罗列一下可用的结构体初始化的方式。对结构体struct A { int b; int c; }有几种初始化方式:第一种:struct A a = { .b = 1, ...
  • 在Java,有两种初始化块:静态初始化块和非静态初始化块. 静态初始化块:使用static定义,当类装载到系统时执行一次.若在静态初始化初始化变量,那仅能初始化类变量,即static修饰的数据成员. 非静态初始化块:...
  • 在pytorch,有自己默认初始化参数方式,所以在你定义好网络结构以后,不进行参数初始化也是可以的。 1.Conv2d继承自_ConvNd,在_ConvNd,可以看到默认参数就是进行初始化的,如下图所示 2.torch.nn.B...
  • 在刚开始学习c语言的时候,会遇到数组是否初始化的情况,若初始化数组的一些元素,则其他元素为0,参见以下程序编译运行就知道他们的区别何在 #include <stdio.h>//数组初始化与未初始化的比较 void ...
  • Java HashMap 初始化

    千次阅读 2020-06-02 13:29:21
    Java HashMap 初始化 1、HashMap 初始化的文艺写法 HashMap 是一种常用的数据结构,一般用来做数据字典或者 Hash 查找的容器。普通青年一般会这么初始化: HashMap<String, String> map = new HashMap&...
  • c++初始化列表详解

    万次阅读 多人点赞 2018-05-18 18:15:04
    与其他函数不同,构造函数除了有名字,参数列表和函数体之外,还可以有初始化列表,初始化列表以冒号开头,后跟一系列以逗号分隔的初始化字段。 class foo { public: foo(string s, int i):name(s), id(i){} ; //...
  • c++ 子类构造函数初始化及父类构造初始化

    万次阅读 多人点赞 2018-08-30 15:58:50
    我们知道,构造方法是用来初始化类对象的。如果在类没有显式地声明构造函数,...因此,在创建子类对象时,为了初始化从父类继承来的成员变量,编译器需要调用其父类的构造函数。如果子类的构造函数没有显示地调...
  • 构造函数,哪些成员变量一定要通过初始化列表来初始化 构造函数初始化时必须采用初始化列表一共有三种情况, 需要初始化的数据成员是对象(继承时调用基类构造函数) 需要初始化const修饰的类成员 需要...
  • C++对象初始化方式

    千次阅读 2019-03-18 23:34:28
    当对象在创建时获得了一个特定的值,我们说这个对象被初始化初始化不是赋值,初始化的含义是创建变量赋予其一个初始值,而赋值的... 对象初始化可以分为默认初始化、直接初始化、拷贝初始化以及值初始化。 1,...
  • DL之DNN优化技术:DNN权重初始值优化【Xavier初始值】的简介、使用方法详细攻略 目录 【Xavier初始值】的简介 【Xavier初始值】的使用方法 【Xavier初始值】的简介 Xavier Glorot等人的论文推荐...
  • 有一个类A,其数据成员如下: class A { ... private: int a; public: const int b;...则构造函数,成员变量一定要通过初始化列表来初始化的是...构造函数,成员变量一定要通过初始化列表来初始化的有以下几种...
  • Java数组的初始化方式

    千次阅读 2014-07-20 01:05:40
    Java数组的初始化方式  初始化方式有两种: 1、静态初始化初始化时由程序员显式指定每个数组元素的初始值,由系统指定数组长度 2、动态初始化初始化时由程序员只指定数组长度,由系统为数组...
  • C++的指针初始化

    千次阅读 2019-08-04 21:22:56
    需要对指针本身和指针的指向都进行初始化,既要初始化内存地址,也要定义内存的内容。如果不进行指针的初始化,则内存地址随机分配。格根据编译器的不同,会出现警告或者报错不同等级的问题,在编译也可能出现...
  • 在Java,有两种初始化块:静态初始化块和非静态初始化块。它们都是定义在类,用大括号{}括起来,静态代码块在大括号外还要加上static关键字。 非静态初始化块: 作用:给对象进行初始化。对象一建立就运行,且...
  • 声明时为成员变量赋值,那么你一创建对象,这个赋值就进行,而且先于构造...执行父类静态代码,执行子类静态代码初始化父类成员变量(我们常说的赋值语句)初始化父类构造函数 初始化子类成员变量 初始化子类构造函数...
  • javaString初始化

    千次阅读 2018-03-15 11:35:08
     只是声明了一个String的引用型变量,并未初始化(作为对象属性时会有默认的隐式初始化str=null),如果后面未用此变量编译会通过String str=”“; 正常的字符串初始化,只不过字符串内容为空。...
  • JavaList初始化

    千次阅读 2020-01-08 22:10:14
    构造List后使用List.add初始化2.使用 {{}} 双括号语法3.使用 Arrays.asList4. 使用 Stream (JDK8)5. 使用 Lists (JDK9) 1.构造List后使用List.add初始化 List<String> stringList = new LinkedList<>...
  • c++变量未初始化的隐患

    千次阅读 2018-03-06 15:42:08
    变量未初始化是C++编程最为常见和易犯的错误之一。但是对于全局变量,我们可以不进行初始化,这个变量会默认的用零进行初始化,但是这通常不是一个好的习惯。我们今天先不探讨全局变量还是静态全局变量。那么对于...
  • 1. 一个类初始化顺序 (静态变量、静态初始化块)=>(变量、初始化块、构造器)。 2. 两个具有继承关系类的初始化顺序 父类的(静态变量、静态初始化块)=> 子类的(静态变量、静态初始化块)=> 父类的(变量...
  • 派生类不能直接访问基类的私有成员,而必须通过基类方法进行访问...C++使用初始化列表完成这项工作。RatedPlayer::RatedPlayer(int r, const string &fn):TableTennisPlayer(fn) { rating = r; }其中TableTennisPlayer
  • 来定义变量时,可以利用变量初始化函数来实现对 initializer 的赋值。 在神经网络,最常权重赋值方式是 正态随机赋值 和 Xavier赋值。 1. 变量初始化函数 tf.random_normal_initializer(shape,mean=0.0,stddev...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 255,734
精华内容 102,293
关键字:

初始化中