我在一些视频中发现了以下代码,我对此非常感兴趣。
#include <iostream>
using namespace std;
#define LIST1(T1) Node<T1,Null>
#define LIST2(T1,T2) Node<T1,LIST1(T2)>
#define LIST3(T1,T2,T3) Node<T1,LIST2(T2,T3)>
#define LIST4(T1,T2,T3,T4) Node<T1,LIST3(T2,T3,T4)>
struct Null { };
template <int X, typename Next>
struct Node {
static const int val = X;
typedef Next Next_;
};
template <typename List>
struct Sum
{
static const int sum = List::val + Sum<typename List::Next_>::sum;
};
template <>
struct Sum<Null> {
static const int sum = 0;
};
int main()
{
cout << Sum<LIST4(2, 2, 3, 4)>::sum << endl;
}
我的问题是,有什么更好的方法呢?还有什么其他方法可以做类似的解析?我看到的主要问题是使用预处理器指令来定义类型。有没有其他方法可以这样做?
例如,我想表示与上面相同的IP地址:
Sum<IP<120.100.10.20>>
将解析输入。
此外,如果可以从文件中获取它,它将更有用。我认为应该允许这种格式化数据在TMP中作为类型。我如何修改代码以支持它?
编辑 ::添加另一个让我觉得有用的代码。
#include <iostream>
#define LIST1(T1) Node<T1,Null>
#define LIST2(T1,T2) Node<T1,LIST1(T2)>
#define LIST3(T1,T2,T3) Node<T1,LIST2(T2,T3)>
#define LIST4(T1,T2,T3,T4) Node<T1,LIST3(T2,T3,T4)>
using namespace std;
// Highest bit in an IP address
template <typename List, int N, bool B>
struct highestBitSet
{
static const bool b = List::val & (1 << N);
static const int bit = highestBitSet<List, N - 1, b>::bit;
};
template <typename List, int N>
struct highestBitSet<List,N,true>
{
static const int bit = N+1;
};
template <typename List>
struct highestBitSet<List, -1, false>
{
static const int bit = 8+highestBitSet<List::Next_, 7, false>::bit;
};
template <int X>
struct highestBitSet<Null, X, false>
{
static const int bit = 0;
};
int main()
{
// Will print 0
cout << highestBitSet<LIST4(1, 0, 0, 0), 7, false>::bit << endl;
// WIll print 31
cout << highestBitSet<LIST4(0, 0, 0, 255), 7, false>::bit << endl;
return 0;
}
答案 0 :(得分:3)
我的问题是,有什么更好的方法呢?还有什么其他方法可以做类似的解析?我看到的主要问题是使用预处理器指令来定义类型。有没有其他方法可以这样做?
使用C ++ 17的折叠表达式,或者如果C ++ 17不可用,则使用C ++ 14 constexpr
:
#include <iostream>
template<int... N> int_list { };
template<int... N> int_list<N...> list() { return {}; }
template<int... N>
int sum(int_list<N...>)
{
#if __cplusplus > 201402L
return (N + ...);
#else
const int vals[] = { N... };
int sum = 0;
for (auto v : vals)
sum += v;
return sum;
#endif
}
int main()
{
std::cout << sum( list<2, 2, 3, 4>() ) << std::endl;
}
例如,我想表示与上面相同的IP地址:
Sum<IP<120.100.10.20>>
将解析输入。
您不需要IPv4地址的可变长度列表,它总是有四个组件。你展示的代码不做任何解析......这将是一个完全不同的问题。将四个单独的参数传递给像LIST4(120, 100, 10, 20)
这样的宏或函数与编写120.100.10.20
完全不同,example.run(function($rootScope, $state){
var arrState = [];
var states = $state.stateRegistry.states;
angular.forEach(states, function(key, value) {
if (value !== "") {
arrState.push(value)
}
});
$rootScope.$on('$locationChangeSuccess', function(){
var n = !$state.current.name ? 1 : arrState.indexOf($state.current.name) + 1;
$rootScope.next = arrState[n];
var p = !$state.current.name ? 0 : arrState.indexOf($state.current.name) - 1;
if (p <0 ) p = 0;
$rootScope.previous = arrState[p];
});
$rootScope.goNext = function () {
$state.go($rootScope.next);
}
$rootScope.goPrevious = function () {
$state.go($rootScope.previous);
};
});
甚至不是有效的C ++令牌。
此外,如果可以从文件中获取它,它将更有用。我认为应该允许这种格式化数据在TMP中作为类型。我如何修改代码以支持它?
从文件中读取数据是一种运行时效果,您无法将模板(编译时)与I / O(运行时)结合起来。