当前位置:首页 > 图灵资讯 > 技术篇> chromium template_util.h 解析
chromium template_util.h 解析
发布时间:2023-05-24 09:24:21
// Copyright (c) 2011 The Chromium Authors. All rights reserved.// Use of this source code is governed by a BSD-style license that can be// found in the LICENSE file.#ifndef BASE_TEMPLATE_UTIL_H_#define BASE_TEMPLATE_UTIL_H_#include <cstddef> // For size_t.#include "build/build_config.h"namespace base {// template definitions from tr1template<class T, T v>struct integral_constant { static const T value = v; typedef T value_type; typedef integral_constant<T, v> type;};template <class T, T v> const T integral_constant<T, v>::value;最基本的true/false 类型, 内部有static,内部有static。 bool成员= true/false, 其他trait类型根据匹配结果继承相应的true_type/false_typetypedef integral_constant<bool, true> true_type;typedef integral_constant<bool, false> false_type;假如T是指针,模板匹配会特偏化匹配到第二个,继承true_typetemplate <class T> struct is_pointer : false_type {};template <class T> struct is_pointer<T*> : true_type {};// Member function pointer detection up to four params. Add more as needed// below. This is built-in to C++ 11, and we can remove this when we switch.判断一个函数是否为某一类成员函数(最多4个参数)template<typename T>struct is_member_function_pointer : false_type {};假如下面的模板匹配没有匹配,它被认为是一个非类成员函数, false_type第一次知道原来的模板可以用到这个程度,甚至可以表示类成员函数。0参数templatete <typename R, typename Z>struct is_member_function_pointer<R(Z::*)()> : true_type {};template <typename R, typename Z>struct is_member_function_pointer<R(Z::*)() const> : true_type {};1参数templatete <typename R, typename Z, typename A>struct is_member_function_pointer<R(Z::*)(A)> : true_type {};template <typename R, typename Z, typename A>struct is_member_function_pointer<R(Z::*)(A) const> : true_type {};templatete2参数 <typename R, typename Z, typename A, typename B>struct is_member_function_pointer<R(Z::*)(A, B)> : true_type {};template <typename R, typename Z, typename A, typename B>struct is_member_function_pointer<R(Z::*)(A, B) const> : true_type {};templatete3参数 <typename R, typename Z, typename A, typename B, typename C>struct is_member_function_pointer<R(Z::*)(A, B, C)> : true_type {};template <typename R, typename Z, typename A, typename B, typename C>struct is_member_function_pointer<R(Z::*)(A, B, C) const> : true_type {};templatete4参数 <typename R, typename Z, typename A, typename B, typename C, typename D>struct is_member_function_pointer<R(Z::*)(A, B, C, D)> : true_type {};template <typename R, typename Z, typename A, typename B, typename C, typename D>struct is_member_function_pointer<R(Z::*)(A, B, C, D) const> : true_type {};判断class T 与 class U是否为同一类型,template <class T, class U> struct is_same : public false_type {};template <class T> struct is_same<T,T> : true_type {};判断数组类型templatete是否为数组类型<class> struct is_array : public false_type {};template<class T, size_t n> struct is_array<T[n]> : public true_type {};template<class T> struct is_array<T[]> : public true_type {};判断是否为non const template引用template引用 <class T> struct is_non_const_reference : false_type {};template <class T> struct is_non_const_reference<T&> : true_type {};template <class T> struct is_non_const_reference<const T&> : false_type {};判断const类型templatete是否属于const类型 <class T> struct is_const : false_type {};template <class T> struct is_const<const T> : true_type {};判断是否为voidtemplatetetet <class T> struct is_void : false_type {};template <> struct is_void<void> : true_type {};namespace internal {// Types YesType and NoType are guaranteed such that sizeof(YesType) <// sizeof(NoType).正如注释所说,必须保证yestype和Notype的size不同,以后才能有效使用.typedef char YesType;struct NoType { YesType dummy[2];};// This class is an implementation detail for is_convertible, and you// don't need to know how it works to use is_convertible. For those// who care: we declare two different functions, one whose argument is// of type To and one with a variadic argument list. We give them// return types of different size, so we can use sizeof to trick the// compiler into telling us which function it would have chosen if we// had called it with an argument of type From. See Alexandrescu's// _Modern C++ Design_ for more details on this sort of trick.converthelper本质上是利用C++本身的函数参数转换,从实现中也可以看出,不同类型的Test函数是基于适应不同类型的。如果From类型可以在函数参数传输中转换为To,则为Yestype, 否则Notype, 而 Create函数的作用纯粹是传递From类型。struct ConvertHelper { template <typename To> static YesType Test(To); template <typename To> static NoType Test(...); template <typename From> static From& Create();};这个trait参考了boost库的is_class, 它的前提是只有class/union/struct,它将包含一个void(C::*)(void)类型函数, 所以下面的Test在模板匹配时会匹配到第一个Test函数,返回Yestype, 相反,返回Notype, 实际使用时要注意,调用的是Test<T>(0)// Used to determine if a type is a struct/union/class. Inspired by Boost's// is_class type_trait implementation.struct IsClassHelper { template <typename C> static YesType Test(void(C::*)(void)); template <typename C> static NoType Test(...);};} // namespace internal// Inherits from true_type if From is convertible to To, false_type otherwise.//// Note that if the type is convertible, this will be a true_type REGARDLESS// of whether or not the conversion would emit a warning.流程如下:首先,ConvertHelperper::Create<From>()获得From类型,然后ConvertHelper::Test<To>(From类型)看能不能转换。如果可以,返回yestype,使is_convertible的struct变成integral_constant<bool,true>,以后可以通过is_convertible的value获得true/false.template <typename From, typename To>struct is_convertible : integral_constant<bool, sizeof(internal::ConvertHelper::Test<To>( internal::ConvertHelper::Create<From>())) == sizeof(internal::YesType)> {};与上述原理相同,true//通过返回type和yestype是否size获得true/falsetemplate <typename T>struct is_class : integral_constant<bool, sizeof(internal::IsClassHelper::Test<T>(0)) == sizeof(internal::YesType)> {};template<bool B, class T = void>struct enable_if {};template<class T>struct enable_if<true, T> { typedef T type; };} // namespace base#endif // BASE_TEMPLATE_UTIL_H_
ps 图灵课堂老师从近一百套最新一线互联网公司面试题中精选而出,涵盖Java架构面试 所有技术栈,包括JVM,Mysql,并发,Spring,Redis,MQ,Zookeeper,Netty, Dubbo,Spring Boot,Spring Cloud,数据结构与算法,设计模式等相关技术领域的大 厂面试题及详解。 详情咨询客服获取全套面经试题。
最新资讯
查看更多-
1
chromium template_util.h 解析
-
2
TEMP_FAILURE_RETRY 宏
-
3
git submodule的使用
-
4
如何通过Java代码将 PDF 转为 HTML 格式
-
5
关于多个项目使用同一个nacos的解决方法
-
6
MYSQL设置密码时显示Failed! Error: SET PASSWORD has no significance for user 'root'@'localhos
-
7
MYSQL设置密码时显示Failed! Error: SET PASSWORD has no significance for user 'root'@'localhos
-
8
Java核心之多态
-
9
#yyds干货盘点# LeetCode程序员面试金典:二叉树的最小深度
-
10
#yyds干货盘点# LeetCode程序员面试金典:两数之和 II - 输入有序数组