V2EX zzxxisme 的所有回复 第 1 页 / 共 1 页
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
V2EX    zzxxisme    全部回复第 1 页 / 共 1 页
回复总数  18
2022-03-18 19:06:16 +08:00
回复了 ActualAvocado 创建的主题 C++ [C++]为什么 For 循环在调试时执行顺序像个悠悠球?
我猜反向执行是在执行 string 和 vector 的析构函数。可以试着回去的时候看看能不能 step in ?
2022-01-31 01:50:38 +08:00
回复了 amiwrong123 创建的主题 C++ 项目中这样去隐藏类的真正实现 是种好的做法吗?
先说我认为的结论:这种写法的主要目的 并不是 为了隐藏实现,而是为了方便转移、复制、释放一个 ModuleBase 子类的对象。

首先我们有 ModuleBase 这个基类,这个基类可能有很多种不同的子类实现,例如 ModuleBaseImpl 是其中一种实现。但是我用这个 Module 的时候我可能不关心具体实现是怎么样,不关心具体的子类是什么。我只想拿到 ModuleBase 的基类的指针(或者引用)进而能够访问子类的具体实现就好了。如果只是这个需求,我的设计可能就是令到 ModuleBase 的虚函数全部都弄成 纯虚函数 (也就是没有默认实现),然后子类 ModuleBaseImpl 必须实现所有纯虚函数。也就是

```c++
class ModuleBase {
...
virtual void startTimer(int32_t timerId, uint64_t msec) = 0; // 纯虚函数
};

class ModuleBaseImpl : public ModuleBase {
...
void startTimer(int32_t timerId, uint64_t msec) override {
... // 具体实现
}
};
```

然后这样会有一个小问题,就是我用一个 Module 的时候,我必须用 ModuleBase 的指针(或者引用,但如果能用引用,可能就没有我说的这个小问题)。而且用这个指针我还要注意适当的时候 delete 这个指针。但是如果这个指针是被其他人用的,在其他人的函数里面他们未必会 delete 这个指针。所以这个时候我需要弄多一个类,来包装这个 ModuleBase 指针,也就是

```c++
class ModuleBaseWrapper {
~ModuleBaseWrapper() { delete module; }
private:
ModuleBase* module;
};

```

有了这个 ModuleBase Wrapper 之后,这个 Wrapper 在析构的时候会帮忙析构这个 ModuleBase 指针。

最后,回到一开始你说的 ModuleBase 里面包含了一个 android::sp<ModuleBase>impl 的事,这个 android::sp<ModuleBase>使得 ModuleBase 可以当做上面的 ModuleBaseWrapper 来用。
2022-01-28 03:03:42 +08:00
回复了 amiwrong123 创建的主题 C++ std::move 的实现使用到了万能引用?
> 但是我经过了 vs2019 debug 后,发现 c 的类型为 A&&,这是为什么呀?

这个不太清楚怎么回答。我觉得因为你是用 auto&&去接 returnTemp()产生的临时变量,所以 c 的类型就是 A&&。如果你使用 auto 去接,那 c 的类型就是 A 。但我觉得不管 c 的类型是 A&&还是 A ,它都是维持着 A 类对象的一份 local copy ,用起来都是一样。

> _Ty& _Arg 优先级比 _Ty&& _Arg 高

这个我觉得是有条件的。如果参数本身是 A&这样的引用类型,那_y& _Arg 有更高的优先级。如果参数是 A 或者 A&&这样的,_Ty&&有更高的优先级。
2022-01-27 02:11:37 +08:00
回复了 amiwrong123 创建的主题 C++ std::move 的实现使用到了万能引用?
再插一句,如果你把第二个 fun_test 改成
```
template <class _Ty>
void fun_test(_Ty _Arg) { // 这里把&去掉
cout << "left" << endl;
}
```
那么 fun_test(_Ty&&)和 fun_test(_Ty)在匹配 fun_test(a)的时候,编译器会选不出来而报错,因为这两个函数面对 A&的 rank 一样。
2022-01-27 02:07:18 +08:00
回复了 amiwrong123 创建的主题 C++ std::move 的实现使用到了万能引用?
@amiwrong123
> 所以,std::move 只有这一个实现也能正常工作,因为它什么类型都可以接,是吧。附言里我加的这个问题,为什么有了万能引用版本的函数,还能调用到左值引用版本的函数呀?有点不理解了,老哥

这里有两点吧。一个是 _Ty&& 的那个的确能接住所有类型。另一个是,当你还写了一个 _Ty& 版本的函数的情况下,因为 main 函数里面的 fun_test(a)传进去的是 a 的引用,也就是传进去的是 A&,这个情况下,编译器会认为 _Ty& 版本的 fun_test 会比 _Ty&& 版本的 fun_test 有更高的 rank (优先级)去匹配这个 A&。所以正确的说法我觉得是,_Ty&&能够接住所有类型,但是在有其他重载的情况下,_Ty&&不一定有更高的 rank 被用上。你可以看看 https://en.cppreference.com/w/cpp/language/overload_resolution 的 Ranking of implicit conversion sequences 下列举的不同情况。

> 上面这个程序是不是就是你说的意思? constexpr 函数可以赋值给 constexpr 标识符,也可以赋值非常量的标识符(如上程序)
对的。你也可以看看这里最下面给的一些例子: https://en.cppreference.com/w/cpp/language/constexpr
2022-01-26 23:03:39 +08:00
回复了 amiwrong123 创建的主题 C++ std::move 的实现使用到了万能引用?
尝试回答一下:
1. 利用_Ty&&可以接受所有引用类型。如果是左值引用,例如 int&,那么这里"_Ty"就是"int&",整个"_Ty&&"就是"int& &&"。如果是右值引用,例如 int&&,那么_Ty 就是 int 。如果传的是一个值,例如 int ,这样_Ty 也是 int 。
2. std::move 加一个 constexpr 并不意味着返回值一定要加 const ,这个是对函数加的 constexpr ,它意味着这个 std::move 可以在用在一个 constant expression 里面,这样,编译器可以在编译期间进行这个 move 。这个 constexpr 是 c++17 之后加进来的,std::move 是 c++11 就加进来的,我猜可能你看过一些版本是 c++17 之前的?
感觉有几个思路…
1. 首先看自己喜欢哪个方面哪个方向的技术,然后看这个方向有什么可以分享的,这样顺带可以自己学习一波。
2. 自己工作做开的内容是属于哪个方面的,然后从这个方面找相关的技术分享,这样工作量比较轻松。
3. 从别人分享的内容看属于哪个方向的,然后找相关的东西分享。例如 Disruptor 是属于多线程消息传递无锁队列,然后属于这方面的有没有可能更好的队列,然后找到这个 https://github.com/rigtorp/MPMCQueue
2021-10-10 23:44:16 +08:00
回复了 olist 创建的主题 程序员 今天看到一个新发现的有趣的排序算法。
1. 这个论文里面提到这个 新算法 的好处不是在于效率,而是在于它的简单性,以及它的 看上去不是那么正确 的特点,然后这个论文去证明它的正确性。这个算法的确最后把 A 数组进行了升序排序。
2. 你说的第二个算法不是传统认为的冒泡… 冒泡每次 swap 的是相邻的两个数,而你的第二个算法是为`A[i]`找`A[i .. n]`的最小值。
2021-08-30 22:18:28 +08:00
回复了 icemanpro 创建的主题 C++ 如何将 list 的值传给函数的可变参数?
看了其他人的理解,我觉得问题是把一个 list 的所有元素传到一个函数的参数列表,而函数的参数列表是 C 的可变参数。我想的是,既然是传给函数作为参数,list 的长度(也就是参数的数目)应该假设不会很多,于是可以假设一个最大 list 长度。如果是利用 C++,可以写一个模板函数,通过递归的方法一下下把每个元素取出来并用 parameter pack 存着,把所有都拿到之后,然后传给带可变参数的函数。像 5 楼说的,用 parameter pack 要在编译期间确定长度,这个长度就是前面说的最大 list 长度。

然后试着写了一下: https://gist.github.com/zzxx-husky/40a42457c01b86f388974a14278dc78e
2021-08-30 18:21:44 +08:00
回复了 icemanpro 创建的主题 C++ 如何将 list 的值传给函数的可变参数?
这个问题问得不知道怎么回答,因为描述不清楚,可以有很多种理解,例如是把整个 list 当做一个参数传给函数,还是把 list 的每个元素拿出来传给函数的每个参数?你的 list 和函数的签名是怎样的?最好能给段代码来表明你要做的事情,还有你做过什么样的尝试,这些尝试有什么问题。
2021-08-27 19:54:13 +08:00
回复了 Hconk 创建的主题 C++ 看到一段挺有意思的 C++代码
尝试说一下我的理解。
1. 首先 [](){} 这样就是创建了一个 不接受任何输入,什么都不做,没有任何输出的 lambda
2. 然后 [](){} () 就是调用了一下上面说 lambda

剩下的就是在加 attributes

3. lambda 声明返回值类型的地方是可以加 attribute 的,例如加一个[[noreturn]]就是 []() [[noreturn]] {}。而 [[ ]] 就是…加 0 个 attribute 。
4. 大括号里面的执行体里面也可以加 attribute,而且可以一次加多个,例如同时加 likely, fallthrough 就是 [[ likely, fallthrough ]]。而 [[ , , , ]] 就是…什么 attribute 也没有加。
5. 找了一份 C++ standard draft 看了一下 lambda expression 的定义,捕捉列表和参数列表应该是不可以加 attribute 的。我找的是这份 draft: https://eel.is/c++draft/expr.prim.lambda#nt:lambda-specifiers,可以看到 lambda-introducer (也就是捕捉列表)和 parameter-declaration-clause (就是 lambda-declarator 里面)之间是没说可以放东西的。
2021-08-03 11:21:06 +08:00
回复了 zzxxisme 创建的主题 C++ 迫于生计,分享一个自己的 C++ LINQ API 实现
@c0xt30a 是 lazy 的。针对你的例子,
1. 第一个遍历 container 的操作就是翻译成

for (auto& i : container) {
...
}

2. 第二个 take_first(3)的操作是翻译成

num = 3
...
if (num-- != 0) {
...
} else {
break
}
...

3. 第三个 max_reduce 的操作就是翻译成

max = std::nullopt
...
if (!max || *max < x) {
max = x
}

然后把所有逻辑嵌套起来之后,就是下面这样:

num = 3
max = std::nullopt
for (auto& i : container) {
if (num-- != 0) {
if (!max || *max < i) {
max = i
}
} else {
break
}
}

按照你的例子,我弄了一个新的 example ( https://github.com/zzxx-husky/coll/blob/master/examples/first_n_max.cpp )。虽然不是遍历一个 container,但是也是试图 生成 很多的整数。因为只需要从前 3 个里面找,所以最后其实只生成了 3 个整数。下面是在 WSL 上运行 3 次的结果。

zzxx@zzxx:~/repos/coll/release | master
$ time ./examples/FirstNMax
Int 1 is 463223032
Int 2 is 1934040530
Int 3 is 897990617
The max of the 3 ints is 1934040530

real 0m0.010s
user 0m0.000s
sys 0m0.016s

zzxx@zzxx:~/repos/coll/release | master
$ time ./examples/FirstNMax
Int 1 is 2009885599
Int 2 is 491657854
Int 3 is 58190656
The max of the 3 ints is 2009885599

real 0m0.010s
user 0m0.000s
sys 0m0.000s

zzxx@zzxx:~/repos/coll/release | master
$ time ./examples/FirstNMax
Int 1 is 1704636435
Int 2 is 1382089679
Int 3 is 1782466259
The max of the 3 ints is 1782466259

real 0m0.010s
user 0m0.000s
sys 0m0.000s
2021-08-03 03:07:42 +08:00
回复了 zzxxisme 创建的主题 C++ 迫于生计,分享一个自己的 C++ LINQ API 实现
@3dwelcome 谢谢!其实我做的也不是编程语言层面的东西。我用的也是 C++提供的语法,做一些 api 层面的东西,期望 api 可以想例如 scala 那样的 collection api 的函数式 api 好用,同时性能达到最好。
关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     1070 人在线   最高记录 6679       Select Language
创意工作者们的社区
World is powered by solitude
VERSION: 3.9.8.5 19ms UTC 18:13 PVG 02:13 LAX 10:13 JFK 13:13
Do have faith in what you're doing.
ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86