条款 01:视 C++为一个语言联邦, view C++ as a federation languages
条款 02:尽量以 const enum inline 替换 #defines, prefer const, enum and inline to #defines
C++ 四个语言层次: 1. C 为基础; 2. Object-Oriented C++ 面向对象的; 3. Template C++; 4. STL: Standard Template Library;
C++ 高效编程守则视状况而定, 取决于你使用 C++的哪种次语言
#include "mainwindow.h"
#include <QApplication>
#include <QDebug>
extern "C" {
// 一般还会在 extern 之前加上 cplusplus
static void dofirst(int iva)
{
qDebug() <<"** Hello World .." <<iva <<__FILE__ <<__LINE__;
}
}
// 这是一个会在 main函数之前调用的函数
__attribute__((constructor)) static int funs_before()
{
qDebug() <<"** Hold on, Please .. this is first one function ..";
return 0;
}
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow w;
w.show();
// 这里调用 dofirst
dofirst(99);
return a.exec();
}
至于,哪里是 C, 哪里是 C++?是不是不那么重要了?
四个层次就像我们接触语言的过程,VC6 == VS2015 == VS2018 == VSCode, Notepad++, EClipse, QtCreator 等,相信绝对多数的兄弟在实际工作中用过vc6.0, 肯定有人也会说没有 class就不叫 C++, 但是C 中有 struct class
#ifndef ECPPCLASS_H
#define ECPPCLASS_H
#include <QObject>
#define GD_VERSION "v1.1.1beta"
#define MAXVALUE(a, b) ((a) > (b) ? (a) : (b))
class EcppClass : public QObject
{
Q_OBJECT
public:
explicit EcppClass(QObject *parent = nullptr);
private:
int value0;
int value1;
bool m_Flag;
};
#endif // ECPPCLASS_H
至此,一个简单的 class EcppClass,继承于 QObject,有构造方法,有私有成员,同时还有两个宏,简单的宏使用还是没什么问题的,展示一下问题吧,可以运行一下问题,是不是你要的结果,bug 是永恒存在的,只是有没有正确的面对他们,他们也是很可爱的存在。。
...
float a = 1, b = 2;
qDebug() <<" a=" <<a <<" b="<<b;
qDebug() <<" MAXVALUE" <<MAXVALUE(a, b) <<MAXVALUE(a ++, b);
qDebug() <<" a=" <<a <<" b="<<b;
...
但是曾经还可以宏写成这个样子。。
//============basic===================
//
#define LOG_ERROR(log_fmt, log_arg ...) \
do{ \
_cDebug(LL_ERROR, "[%s] " log_fmt "\n", __FUNCTION__, ##log_arg); \
} while (0)
#define LOG_WARN(log_fmt, log_arg ...) \
do{ \
_cDebug(LL_WARN, "[%s] " log_fmt "\n", __FUNCTION__, ##log_arg); \
} while (0)
#define LOG_NOTICE(log_fmt, log_arg ...) \
do{ \
_cDebug(LL_NOTICE, "[%s] " log_fmt "\n", __FUNCTION__, ##log_arg); \
} while (0)
#define LOG_INFO(log_fmt, log_arg ...) \
do{ \
_cDebug(LL_INFO, "[%s] " log_fmt "\n", __FUNCTION__, ##log_arg); \
} while (0)
#define LOG_DEBUG(log_fmt, log_arg ...) \
do{ \
_cDebug(LL_DEBUG, "[%s] " log_fmt "\n", __FUNCTION__, ##log_arg); \
} while (0)
//============extend===================
关于const 关键字,下次一起说吧。。写一下 inline function。。
inline bool getCurrentFlag() {
return this->m_Flag;
}
inline void setValue(int vl0, int vl1) {
value0 = vl0;
value1 = vl1;
}
备:
1. inline 的使用是有所限制的,inline 只适合涵数体内代码简单的涵数使用,不能包含复杂的结构控制语句例如 while、switch,并且不能内联函数本身不能是直接递归函数(即,自己内部还调用自己的函数)。
2. inline 函数仅仅是一个对编译器的建议,所以最后能否真正内联,看编译器的意思,它如果认为函数不复杂,能在调用点展开,就会真正内联,并不是说声明了内联就会内联,声明内联只是一个建议而已。
坑是天天有,如今特别多
鉴于大家水平都不低,小弟就不卖弄了,写给新手些话吧。。
1. C++ 四个等级,可以参考一下 stl 的标准库源码,找不到的话,看看Qt sdk里的也行,至少源码比较好找。。书中写的也许可以称为语言的极限,效率和复杂度,其实是矛盾的,看这样的书,不能将其与 windows 编程大全或是 C++标准库来看,毕竟方向不同。。
2. enum 和 inline,对比的话,还是 enum 更常用些,毕竟头文件里写上一大堆的 #define ,可读性就变差了,而且针对 C++的封装性来说也不是很友好的。。inline 本人是不太喜欢用的,因为总感觉没啥作用,而且有些编译器也会对函数有所优化,虽然看不到,但是编译的时候 -O 还是个现实的存在。。
3. 越来越觉得,代码习惯尤其重要,上学时老师教的,基本也都没啥用了,还得实习期的时候,那时在公司一家小公司做 ios 开发,刚刚开始有点开窍了,又忙着写毕业论文,答辩的时候,老师问我找到实习了吗? 我就说了一下,对于 object-c 学校老师竟然表示不了解,好吧。。后来到了家外企,第一次被现实打脸,功能写完,还被打回 2次,最后还是老大给我审代码,获益匪浅,必须顶礼膜拜。。
4. 这才是这本书的开始,刚写 2条条款,希望可以获得大家关注哈,大佬们欢迎指点一二。。