现代C++教程2023

2023-05-16

文章目录

  • 2.C++默认实参
  • 21.模板模板形参
  • 22.C++11形参包
  • 24.std::nothrow
  • 25.std::call_once与pthread_once

2.C++默认实参

21.模板模板形参

模板参数:是一个模板类型

// Type your code here, or load an example.
#include <string>
#include <iostream>

template<typename T>
struct X{};



template<typename Z, template<typename T> typename C>
struct Y{
    C<Z> c;
};

template<class T>
struct X2{
    T t;
};


template<template<typename T, typename T2, typename T3> typename S>
struct Str{
    S<char, std::char_traits<char>, std::allocator<char>> str;
};


int main()
{
    Y<int, X2> y{};
    y.c.t=100;
    std::cout<<y.c.t<<'\n';

	//使用std::string error,因为别名的话,与Str类模板的参数不匹配,可以调试看看
    Str<std::basic_string> s;
    s.str="abc";
    std::cout<<s.str<<'\n';
}

22.C++11形参包

#include <sstream>                     
#include <string>
#include <iostream>

using namespace std;
// link:https://en.cppreference.com/w/cpp/language/parameter_pack

// type ... pack-name (optional)	(1)	
template<size_t...args>
struct X{
    void f(){
        // pattern ...	(6)	
        for(const auto& i: {args...})
        {
            std::cout<<i<<' ';
            std::cout<<'\n';
        }
    }
};

// typename|class ... pack-name (optional)	(2)	
// pack-name ... pack-param-name (optional)	(5)	
template<typename...Args>
void f(Args...args)
{
    ((std::cout<<args<<' '),...);//折叠表达式
}

// type-constraint ... pack-name (optional)	(3)	(since C++20)
// template<std::integral ...Args>
// void f2(Args...args)
// {
//     ((std::cout<<args<<' '),...);
// }

// template < parameter-list > typename|class ... pack-name (optional)	(4)	(since C++17)
template<typename T1, typename T2>
struct T{};

template<template<typename T1, typename T2>typename...Args>
struct Y{};


// pattern ...	(6)	递归展开
void print(){}
template<typename T, typename ...Args>
void print(T t, Args...args)
{
    std::cout<<t<<' ';
    print(args...);
}

template<size_t...Args>
void t()
{
    int array[sizeof...(Args)]{Args...};
    for(auto const& i: array)
    {
        std::cout<<i<<' ';
    }
    endl(std::cout);
}

int main()
{
    X<1,2,3> x;
    x.f();
    f(4,5,6,"wangji");
    // f2(7);
    Y<std::basic_string,T,T>y;
    endl(std::cout);
    print('a','b');
    t<1,2>();
}

24.std::nothrow

  • ref:C++中nothrow的介绍及使用

当使用new申请一块内存失败时,抛出异常std::bad_alloc是C++标准中规定的标准行为,所以使用try { p = new int[size];} catch(std::bad_alloc) { … } 的处理方式。

std::nothrow与标准new的区别是,new在分配内存失败时会抛出异常,而"new(std::nothrow)"在分配内存失败时会返回一个空指针。

new operator分配内存失败后,缺省的行为不是返回NULL,而是抛出异常std::bad_alloc。所以判断返回值是否为NULL没有任何意义

#include <iostream>
#include <new> // std::nothrow
 
// reference: http://www.cplusplus.com/reference/new/nothrow/
int test_nothrow1()
{
	std::cout << "Attempting to allocate 1 MiB...";
	char* p = new (std::nothrow) char[1048576];
	if (p == 0)
		std::cout << "Failed!\n";
	else {
		std::cout << "Succeeded!\n";
		delete[] p;
	}
 
	return 0;
}
 
// reference: http://en.cppreference.com/w/cpp/memory/new/nothrow
int test_nothrow2()
{
	try {
		while (true) {
			new int[100000000ul];   // throwing overload
		}
	}
	catch (const std::bad_alloc& e) {
		std::cout << e.what() << '\n';
	}
 
	while (true) {
		int* p = new(std::nothrow) int[100000000ul]; // non-throwing overload
		if (p == nullptr) {
			std::cout << "Allocation returned nullptr\n";
			break;
		}
	}
 
	return 0;
}

25.std::call_once与pthread_once

pthread_once可以实现多线程的单例,且可以在函数中注册好单例对象的退出函数;

  • ref:muduo:Singleton.h
  • has_no_destroy
// Use of this source code is governed by a BSD-style license
// that can be found in the License file.
//
// Author: Shuo Chen (chenshuo at chenshuo dot com)

#ifndef MUDUO_BASE_SINGLETON_H
#define MUDUO_BASE_SINGLETON_H

#include <assert.h>
#include <pthread.h>
#include <stdlib.h>  // atexit

#include "muduo/base/noncopyable.h"

namespace muduo {

namespace detail {
// This doesn't detect inherited member functions!
// http://stackoverflow.com/questions/1966362/sfinae-to-check-for-inherited-member-functions
template <typename T>
struct has_no_destroy {
  template <typename C>
  static char test(decltype(&C::no_destroy));

  template <typename C>
  static int32_t test(...);

  const static bool value = sizeof(test<T>(0)) == 1;
};
}  // namespace detail

template <typename T>
class Singleton : noncopyable {
 public:
  Singleton() = delete;
  ~Singleton() = delete;

  static T& instance() {
    pthread_once(&ponce_, &Singleton::init);
    assert(value_ != NULL);
    return *value_;
  }

 private:
  static void init() {
    value_ = new T();
    if (!detail::has_no_destroy<T>::value) {
      ::atexit(destroy);
    }
  }

  static void destroy() {
    typedef char T_must_be_complete_type[sizeof(T) == 0 ? -1 : 1];
    T_must_be_complete_type dummy;
    (void)dummy;

    delete value_;
    value_ = NULL;
  }

 private:
  static pthread_once_t ponce_;
  static T* value_;
};

template <typename T>
pthread_once_t Singleton<T>::ponce_ = PTHREAD_ONCE_INIT;

template <typename T>
T* Singleton<T>::value_ = NULL;

}  // namespace muduo

#endif  // MUDUO_BASE_SINGLETON_H

std::call_once功能类似于pthread_once,但是单例对象的析构还得使用atexit

  • std::call_once函数第一个参数是std::once_flag的一个对象,第二个参数可以是函数、成员函数、函数对象、lambda函数。
template< class Function, class... Args >
void call_once ( std::once_flag& flag, Function&& f, Args&& args... );
参数解析:
flag     -	 an object, for which exactly one function gets executed
f	 -	 需要被调用的函数
args...  -	 传递给函数f的参数(可以多个)
返回值为 (none)
抛出异常
std::system_error if any condition prevents calls to call_once from executing as specified any exception thrown by f

#include <iostream>
#include <thread>
#include <mutex>
 
std::once_flag flag1;
 
void simple_do_once()
{
    std::call_once(flag1, [](){ std::cout << "Simple example: called once\n"; });
}
 
int main()
{
    std::thread st1(simple_do_once);
    std::thread st2(simple_do_once);
    std::thread st3(simple_do_once);
    std::thread st4(simple_do_once);
    st1.join();
    st2.join();
    st3.join();
    st4.join();
}

参考:

  • 现代C++教程 2023
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

现代C++教程2023 的相关文章

随机推荐

  • Gtest输出单元测试报告和输出覆盖率报告

    文章目录 1 要求2 生成gtest测试报告3 生成gtest覆盖率报告 1 要求 编译工具 xff1a 选择Cmake xff0c 单元测试使用Gtest 2 生成gtest测试报告 gtest本身仅能输出xml或者json格式的测试报告
  • GTEST/GMOCK介绍与实战:Gtest Sample10

    文章目录 1 简介2 用法 1 简介 示例 10展示了如何使用侦听器API来实现基本内存泄漏检查 2 用法 span class token comment This sample shows how to use Google Test
  • Bitbake与Yocto

    文章目录 一 Bitbake二 Yocto 一 Bitbake xff08 1 xff09 使用教程可以参考 xff1a BitBake 实用指南 xff0c 大部分步骤跟着操作即可了解bitbake的工作流程 xff1b 他主要参考和翻译
  • 随机漫步

    span class token keyword import span numpy span class token keyword as span np span class token keyword import span rand
  • UTC时间和PTP精确时间协议

    文章目录 一 GMT二 UTC三 GMT vs UTC四 C 43 43 获得当前的UTC时间 一 GMT GMT xff08 Greenwich Mean Time xff09 xff0c 格林威治平时 xff08 也称格林威治时间 xf
  • AutoSar系列之:AutoSar发展

    文章目录 一 Autosar成员二 Autosar历史发展三 使用Autosar前的状态1 原始状态2 进阶状态 四 使用Autosar后的状态1 软硬件隔离2 Autosar优势 一 Autosar成员 二 Autosar历史发展 三 使
  • AutoSar系列之:AutoSar概述

    文章目录 一 Autosar是什么二 架构 一 Autosar是什么 RTE xff1a 用与传递应用层软件和基础软件从之间的信号的 xff1b 隔离应用软件层和基础软件层 xff1b 其中一个层修改了 xff0c 不会影响另外一个层 xf
  • Autosar系列之Appl概述

    文章目录 一 Appl的组成1 SWC通信2 SWC分配 一 Appl的组成 SWC xff1a 应用软件组件 Autosar接口 xff1a SWC之间连接的端口 Runnable xff1a 可运行实体 xff0c SWC里面的一些函数
  • Autosar系列之SWC类型

    文章目录 一 原子级SWC二 集合级SWC三 特殊的SWC 一 原子级SWC 含义 xff1a 不可拆解的SWC 二 集合级SWC eg xff1a 将相似的功能放在一起 三 特殊的SWC IoHwAb xff0c Cdd 在原有的Auto
  • 汽车操作系统

    文章目录 一 汽车控制器类型二 Hypervisor三 QNX Linux Andorid四 Automotive Grade Linux 系统 xff08 AGL xff09 1 介绍2 IVI市场现状3 系统构建 xff08 1 xff
  • Autosar系列之Ports类型

    文章目录 一 接口二 接口类型三 S R接口四 C S 接口 一 接口 接口是连接2个SWC通信的 二 接口类型 三 S R接口 发送 接受数据传输接口 一般通过全局变量才传递 四 C S 接口 客户 服务接口 xff1b 通过函数Runn
  • Autosar系列之Runnable可运行实体

    文章目录 一 RUnnable Entity 一 RUnnable Entity 可运行实体 xff0c 其实就是 C文件内的函数而已 一个SWC可以包含多个Runnable Entity xff0c 就是一个 C文件中可以包含多个函数 x
  • Autosar系列之RTE

    文章目录 一 RTE二 RTE功能 一 RTE RTE Run TIme Environment 是Autosar体系结构的核心 RTE是Autosar软件架构中 xff0c 介于应用层和基础软件层之间 xff0c 是Autosar虚拟功能
  • Autosar系列之Autosar应用层整体入门

    文章目录 一 整个功能示意图二 软件组件SWC分类三 SWC组件 xff1a ports1 发送 接收端口Sender Receiver2 客户端 服务端端口Client Server 四 可运行实体Runnables五 BSW1 微控制器
  • ubuntu下mysql数据库的设置

    gt su root gt mysql span class token operator span u root span class token operator span p gt show databases span class
  • Python装饰器Decorators

    文章目录 一 功能二 64 语法糖三 args kwargs四 带参数的装饰器五 类装饰器六 装饰器顺序 一 功能 装饰器本质上是一个 Python 函数或类 xff0c 它可以让其他函数或类在不需要做任何代码修改的前提下增加额外功能 xf
  • Autosar系列之Developer工具

    文章目录 一 什么是DaVinci Developer xff1f 二 DaVinci Developer Workspace三 Software Conponent xff08 SWC xff09 Design 一 什么是DaVinci
  • vscode中调试rust程序

    文章目录 一 vscode运行和调式rust程序二 常见问题1 rust Request textDocument formatting failed 2 cargo命令3 使用rust gdb调试rust程序4 cargo build太慢
  • Available-Python-Tuf

    文章目录 一 Pyhon tuf二 安装方法三 启动四 一个可用的Python Tuf 一 Pyhon tuf 1 github link 向该Pyhton tuf的repo server上传包不会持久化保存到本地 xff0c 是个demo
  • 现代C++教程2023

    文章目录 2 C 43 43 默认实参21 模板模板形参22 C 43 43 11形参包24 std nothrow25 std call once与pthread once 2 C 43 43 默认实参 21 模板模板形参 模板参数 xf