C++语法小技巧
程序员文章站
2022-06-15 15:07:50
前言 写的很乱,各种内容都有。仅仅是为了记录一下 而且内容极其不严谨(没错,只有实践,没有理论)!请各位谨慎驾驶! 强制内联 本地测试结果: 开O2之后inline和Inline加不加没啥用 不开O2时inline可能会有负优化,而Inline会让程序快很多 当然也可以强制不inline 直接在函数 ......
前言
写的很乱,各种内容都有。仅仅是为了记录一下
而且内容极其不严谨(没错,只有实践,没有理论)!请各位谨慎驾驶!
强制内联
#define inline __inline__ __attribute__((always_inline))
本地测试结果:
开o2之后inline和inline加不加没啥用
不开o2时inline可能会有负优化,而inline会让程序快很多
当然也可以强制不inline
直接在函数名前加
__attribute__((noinline))
利用位运算实现大小写转化
可以这么写
char toupper(char a) {return (a >= 'a' && a <= 'z') ? a ^ ' ' : a;}
实测比c++内置的toupper
快6倍。。
enum类型
这玩意儿叫“枚举”
格式如下:
enum [enumeration name] {enumerator1[=value1], enumerator2[=value2], ...};
其中,第二个变量的取值默认是第一个变量取值+1,第一个默认是0,当然也可以自己设定
一个简单的栗子
enum noip {a, b, c, d = 22}; cout << c << " " << d;
将会输出2 22
自定义输入输出流
这部分有点硬核啊。。
一个简单的栗子是这样的
#include<bits/stdc++.h> using namespace std; class pair { private: int id; string s; public: friend ostream& operator << (ostream& os, pair& a) { os << a.s << ":" << a.id << "\n"; return os; } friend istream& operator >> (istream& is, pair& a) { is >> a.s >> a.id; return is; } }; int main( ) { pair a; cin >> a; cout << a; return 0; } //input: abc 123 //output : abc:123
注意这里我们实际上还是在用cin / cout输入输出
输入输出流在oi中常常应用于输入输出优化。
struct inputoutputstream { enum { size = 1000001 }; char ibuf[size], *s, *t, obuf[size], *oh; inputoutputstream() : s(), t(), oh(obuf) {} ~inputoutputstream() { fwrite(obuf, 1, oh - obuf, stdout); } inline char read() { if (s == t) t = (s = ibuf) + fread(ibuf, 1, size, stdin); return s == t ? -1 : *s++; } template <typename t> inline inputoutputstream &operator>>(t &x) { static char c; static bool iosig; for (c = read(), iosig = false; !isdigit(c); c = read()) { if (c == -1) return *this; iosig |= c == '-'; } for (x = 0; isdigit(c); c = read()) x = x * 10 + (c ^ '0'); if (iosig) x = -x; return *this; } inline void print(char c) { if (oh == obuf + size) { fwrite(obuf, 1, size, stdout); oh = obuf; } *oh++ = c; } template <typename t> inline void print(t x) { static int buf[23], cnt; if (x != 0) { if (x < 0) print('-'), x = -x; for (cnt = 0; x; x /= 10) buf[++cnt] = x % 10 | 48; while (cnt) print((char)buf[cnt--]); } else print('0'); } template <typename t> inline inputoutputstream &operator<<(const t &x) { print(x); return *this; } } io;
template
template,中文名:模板
分为两类,一种叫类模板
,一种叫函数模板
类模板我用的不多
函数模板用的多一些
下面是一个求最大值的模板,c++的标准库中也是这么实现的,因此同时存在的话会引起ce
template <typename t> inline t const& max(t const &a, t const &b) { return a > b ? a : b; }
如果直接调用的话,当\(a, b\)的类型不同时会引起ce。
这时可以直接强制类型转化
int a = 1e9; long long b = 1e18; long long c = max<int>(a, b); //the output is 1e9 int a = 1e9; long long b = 1e18; long long c = max<long long>(a, b); //the output is 1e18
预编译黑科技
第一条是强制开栈空间
后面的并不清楚在干啥,貌似可以强制\(o_2\)
#pragma comment(linker, "/stack:102400000,102400000") #pragma gcc diagnostic error "-std=c++11" #pragma gcc optimize("-fdelete-null-pointer-checks,inline-functions-called-once,-funsafe-loop-optimizations,-fexpensive-optimizations,-foptimize-sibling-calls,-ftree-switch-conversion,-finline-small-functions,inline-small-functions,-frerun-cse-after-loop,-fhoist-adjacent-loads,-findirect-inlining,-freorder-functions,no-stack-protector,-fpartial-inlining,-fsched-interblock,-fcse-follow-jumps,-fcse-skip-blocks,-falign-functions,-fstrict-overflow,-fstrict-aliasing,-fschedule-insns2,-ftree-tail-merge,inline-functions,-fschedule-insns,-freorder-blocks,-fwhole-program,-funroll-loops,-fthread-jumps,-fcrossjumping,-fcaller-saves,-fdevirtualize,-falign-labels,-falign-loops,-falign-jumps,unroll-loops,-fsched-spec,-ffast-math,ofast,inline,-fgcse,-fgcse-lm,-fipa-sra,-ftree-pre,-ftree-vrp,-fpeephole2",3) #pragma gcc target("avx","sse2")
__builtin系列
- __builtin_popcount(unsigned int n)
计算\(n\)的二进制表示中有多少个1
- __builtin_parity(unsigned int n)
判断\(n\)的二进制表示中1的个数奇偶性(要你何用?)
- __builtin_ffs(unsigned int n)
判断\(n\)的二进制末尾最后一个1的位置,从1开始
- __builtin_ctz(unsigned int n)
判断\(n\)的二进制末尾\(0\)的个数
- __builtin_clz(unsigned int n)
判断\(n\)的二进制前导0的个数
上一篇: MYSQL查询解决方法