|
现代C++的一些技巧-大浪淘金
参考 Welcome Back to C++ (Modern C++)
https://docs.microsoft.com/en-us ... tudio-2013/hh279654(v%3dvs.120)
例子有所修改。
测试要添加包含
#include <iostream>
#include <iomanip>
#include <string>
#include <vector>
#include <map>
#include <unordered_map>
#include <memory>
1)一般情况下,避免将 using 指令放置在头文件(*.h) 中,
因为任何包含该标头的文件都会将命名空间中的所有内容引入范围,
这将导致非常难以调试的名称隐藏和名称冲突问题。
using namespace std;
2)与C相关的包含,函数,变量,可以这样表述
extern "C" {
#include <stdio.h>
}
3)几种容器用法,这已经很常见了。
a)vector
vector<string> apples;
apples.push_back("Granny Smith");
b)map
map<string, string> apple_color;
apple_color["Granny Smith"] = "Green";
c)unordered_map
unordered_map<char, int> umap;
umap.insert(unordered_map<char, int>::value_type('a', 1));
umap.insert(unordered_map<char, int>::value_type('b', 2));
umap.insert(unordered_map<char, int>::value_type('c', 3));
cout << "c1.at('a') == " << umap.at('a') << endl;
cout << "c1.at('b') == " << umap.at('b') << endl;
cout << "c1.at('c') == " << umap.at('c') << endl;
4)smart指针,比较流行,特别在DX12SDK中
a)unique_ptr,make_unique
data a[4] = {
{ "1","aaaa", "aaaa"},
{ "2","bbbb", "bbbb" },
{ "3","cccc", "cccc" },
{ "4","dddd", "dddd" }
};
vector<unique_ptr<data>> songs;
songs.push_back(make_unique<data>(a[0]));
songs.push_back(make_unique<data>(a[1]));
songs.push_back(make_unique<data>(a[2]));
songs.push_back(make_unique<data>(a[3]));
cout << "no \tArtist \tTitle " << endl;
for (const auto& song : songs)
{
cout << song->s1<< "\t" << song->s2 << "\t" << song->s3 << endl;
}
b)shared_ptr,make_shared
data b[3] = {
{"1111", "aaaaaaa","111111"},
{"2222", "bbbbbbb","222222"},
{"3333", "ccccccc","333333"}
};
vector<shared_ptr<data>> v{
make_shared<data>(b[0]),
make_shared<data>(b[1]),
make_shared<data>(b[2])
};
for (const auto& s : v)
{
cout << s->s1 << ":" << s->s2 << ":" << s->s3 << endl;
}
5)lambda表达式,写出来很多人都看不懂。高深隐晦,大师的长相。
auto f1 = [](int x, int y) { return x + y; };
cout << f1(2, 3) << endl;
int k = [](int x, int y) { return x + y; }(5, 4);
cout << k << endl;
int m = 0;
int n = 0;
[&, n](int a) mutable { m = ++n + a; }(4);
cout << m << endl << n << endl;
6)mutable修饰字,mutable翻译是易变的;很可能改变的
放在非静态,非常量的类数据成员,可以由常量成员函数赋值
也可以由非常量成员函数赋值。第三方SDK代码中常用。
class ca
{
mutable string s1;
int a;
string s2;
public:
void setcs() const
{
s1 = "aaaaa";
}
void show() {
cout << "s1=" << s1 << endl;
cout << "s2=" << s2 << endl;
s1 = "ccccc";//强制赋值,它是可以地
cout << "s1=" << s1 << endl;
}
void setvs()/* const*/ {
s2 = "bbbbb";//如果不注释const,此处编译器报错,即不能通过常量成员函数赋值
}
};
ca aa;
aa.setcs();
aa.setvs();
aa.show();
7)const修饰, 一般人都会看晕地,包括我自己,是MSDN地,只不过我总结地放在一起。
const char cch = 'A';
char ch = 'B';
//正确
const char *pch1 = &cch;
const char *const pch4 = &cch;
const char *pch5 = &ch;
char *pch6 = &ch;
char *const pch7 = &ch;
const char *const pch8 = &ch;
//加注释地是编译器指明错误地
//char *pch2 = &cch;
//char *const pch3 = &cch;
char *pch2=nullptr;
char *const pch3=nullptr;
pch1 = &ch; // OK: pointer not declared const
*pch2 = 'A'; // OK: normal pointer
pch2 = &ch; // OK: normal pointer
*pch3 = 'A'; // OK: object not declared const
//加注释地是编译器指明错误地
//*pch1 = 'A'; // Error: object declared const
//pch3 = &ch; // Error: pointer declared const
//*pch4 = 'A'; // Error: object declared const
//pch4 = &ch; // Error: pointer declared const
8)自动变量在遍历4种用法,结果都是一样。
int x[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
for (int y : x) {
cout << y << " ";
}
cout << endl;
for (auto y : x) {
cout << y << " ";
}
cout << endl;
for (auto &y : x) {
cout << y << " ";
}
cout << endl;
for (const auto &y : x) {
cout << y << " ";
}
cout << endl;
9)文本自动变量声明,当满篇都是auto的时候,老程序员都看不懂了。
// Character literals
auto c0 = 'A'; // char
auto c1 = u8'A'; // char
auto c2 = L'A'; // wchar_t
auto c3 = u'A'; // char16_t
auto c4 = U'A'; // char32_t
// String literals
auto s0 = "hello"; // const char*
auto s1 = u8"hello"; // const char*, encoded as UTF-8
auto s2 = L"hello"; // const wchar_t*
auto s3 = u"hello"; // const char16_t*, encoded as UTF-16
auto s4 = U"hello"; // const char32_t*, encoded as UTF-32
// Raw string literals containing unescaped \ and "
auto R0 = R"("Hello \ world")"; // const char*
auto R1 = u8R"("Hello \ world")"; // const char*, encoded as UTF-8
auto R2 = LR"("Hello \ world")"; // const wchar_t*
auto R3 = uR"("Hello \ world")"; // const char16_t*, encoded as UTF-16
auto R4 = UR"("Hello \ world")"; // const char32_t*, encoded as UTF-32
// Combining string literals with standard s-suffix
auto S0 = "hello"s; // std::string
auto S1 = u8"hello"s; // std::string
auto S2 = L"hello"s; // std::wstring
auto S3 = u"hello"s; // std::u16string
auto S4 = U"hello"s; // std::u32string
// Combining raw string literals with standard s-suffix
auto S5 = R"("Hello \ world")"s; // std::string from a raw const char*
auto S6 = u8R"("Hello \ world")"s; // std::string from a raw const char*, encoded as UTF-8
auto S7 = LR"("Hello \ world")"s; // std::wstring from a raw const wchar_t*
auto S8 = uR"("Hello \ world")"s; // std::u16string from a raw const char16_t*, encoded as UTF-16
auto S9 = UR"("Hello \ world")"s; // std::u32string from a raw const char32_t*, encoded as UTF-32
10)数字分隔符
//数字分隔符:可以使用单引号字符 (撇号) 分隔中较大的数,
//以使其更易于供人阅读的位置值。 分隔符不会对编译产生任何影响。
//你在数值上面不要乱加,会扰乱阅读者的心神。不知道你在干什么,虽然不影响结果。
long long i = 24'847'458'121;
cout << "i=" << i << endl;
11)C++位域
struct Date {
unsigned nWeekDay : 3; // 0..7 (3 bits)
unsigned nMonthDay : 6; // 0..31 (6 bits)
unsigned : 0; // Force alignment to next boundary.
unsigned nMonth : 5; // 0..12 (5 bits)
unsigned nYear : 8; // 0..100 (8 bits)
};
赋值,取值很简单,但理解它的数据就不很简单。
为了调试在程序首添加
#include <bitset>
using std::bitset;
再添加下面测试
Date date;
ZeroMemory(&date, sizeof(date));
date.nYear = 99;
date.nMonth = 12;
date.nMonthDay =31;
date.nWeekDay = 7;
cout << "sizeof(date)=" << sizeof(date) <<endl;
bitset<64> bs(*(unsigned __int64*)&date);
cout << "date=" << bs.to_string() << endl;
结果:
sizeof(date)=8
date=0000000000000000000011000110110000000000000000000000000011111111
其占8个字节,88,64位,故转(unsigned __int64*)指针。
特别注意中间0,是强制数据在下一个边界分配。
xx_player 2019.5
写东西比答题简单, 好弄。
以上这些,虽然有些时日,仍是流行地。
没看懂就参阅微软的msdn,有机器翻译成中文地,也有英文版地
在里面找,还有很多没介绍地。我也不太懂,会被问地瞠目结舌地,毕竟那东西是微软,
我只是搬运工而已,能搬出来就已经有成就感了。
通过努力,你们再搬一些,你们就可以建高楼。
代码编译在vs2015上测试通过。没有任何问题。
|
上一篇: 软件启动项提示病毒木马下一篇: 数据库之本地数据库
|