Skip to content

Commit

Permalink
50
Browse files Browse the repository at this point in the history
  • Loading branch information
wanghenshui committed Feb 18, 2022
1 parent 3bb5fda commit 87fd736
Show file tree
Hide file tree
Showing 3 changed files with 316 additions and 2 deletions.
8 changes: 6 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,11 @@

每周更新

RSS [xml](https://wanghenshui.github.io/cppweeklynews/feed.xml) [json](https://wanghenshui.github.io/cppweeklynews/feed.xml) 暂时不好使
RSS使用仓库的release RSS [链接](https://github.com/wanghenshui/cppweeklynews/releases.atom )

~~[xml](https://wanghenshui.github.io/cppweeklynews/feed.xml) [json](https://wanghenshui.github.io/cppweeklynews/feed.xml) page rss暂时不好使~~





Expand All @@ -21,7 +25,7 @@ RSS [xml](https://wanghenshui.github.io/cppweeklynews/feed.xml) [json](https://w
| [十一期](./posts/011.md) | [十二期](./posts/012.md) | [十三期](./posts/013.md) | [十四期](./posts/014.md) | [十五期](./posts/015.md) | [十六期](./posts/016.md) | [十七期](./posts/017.md) | [十八期](./posts/018.md) | [十九期](./posts/019.md) | [二十期](./posts/020.md) |
| [二十一](./posts/021.md) | [二十二](./posts/022.md) | [二十三](./posts/023.md) | [二十四](./posts/024.md) | [二十五](./posts/025.md) | [二十六](./posts/026.md) | [二十七](./posts/027.md) | [二十八](./posts/028.md) | [二十九](./posts/029.md) | [三十期](./posts/030.md) |
| [三十一](./posts/031.md) | [三十二](./posts/032.md) | [三十三](./posts/033.md) | [三十四](./posts/034.md) | [三十五](./posts/035.md) | [三十六](./posts/036.md) | [三十七](./posts/037.md) | [三十八](./posts/038.md) | [三十九](./posts/039.md) | [四十期](./posts/040.md) |
| [四十一](./posts/041.md) | [四十二](./posts/042.md) | [四十三](./posts/043.md) | [四十四](./posts/044.md) | [四十五](./posts/045.md) | [四十六](./posts/046.md) | [四十七](./posts/047.md) | [四十八](./posts/048.md) | [四十九](./posts/049.md) | |
| [四十一](./posts/041.md) | [四十二](./posts/042.md) | [四十三](./posts/043.md) | [四十四](./posts/044.md) | [四十五](./posts/045.md) | [四十六](./posts/046.md) | [四十七](./posts/047.md) | [四十八](./posts/048.md) | [四十九](./posts/049.md) | [五十期](./posts/050.md) |



Expand Down
2 changes: 2 additions & 0 deletions posts/049.md
Original file line number Diff line number Diff line change
Expand Up @@ -832,6 +832,8 @@ constexpr能用就用

在嵌入式领域,相关的程序员很爱用u8 来做各种临时计算之类了。他都是临时变量了,u8 u32真的没那么重要

PS : 水友地球补充,实际上有uint_fast8_t这种东西,背后就是unsigned int

- [Our Adventures With REST API in C++ : Making it Easy - Damien Buhl - CppCon 2021](https://www.youtube.com/watch?v=KM9RezKLdVc&list=PLHTh1InhhwT6bY4nS4p7f5b_754myC3ze&index=8)

手把手实现c++ rest api
Expand Down
308 changes: 308 additions & 0 deletions posts/050.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,308 @@
---
layout: post
title: 第50期
---

# C++ 动态新闻推送 第50期

[reddit](https://www.reddit.com/r/cpp/)/[hackernews](https://news.ycombinator.com/)/[lobsters](https://lobste.rs/)/[meetingcpp](https://www.meetingcpp.com/blog/blogroll/items/Meeting-Cpp-Blogroll-317.html)摘抄一些c++动态

[周刊项目地址](https://github.com/wanghenshui/cppweeklynews)[在线地址](https://wanghenshui.github.io/cppweeklynews/)[知乎专栏](https://www.zhihu.com/column/jieyaren) |[腾讯云+社区](https://cloud.tencent.com/developer/column/92884)

弄了个qq频道,[手机qq点击进入](https://qun.qq.com/qqweb/qunpro/share?_wv=3&_wwv=128&inviteCode=xzjHQ&from=246610&biz=ka)

欢迎投稿,推荐或自荐文章/软件/资源等,请[提交 issue](https://github.com/wanghenshui/cppweeklynews/issues)

---

## 资讯

标准委员会动态/ide/编译器信息放在这里

c++ summit在上海要开,三月份,两天套票接近六千,真心贵,这价格,比cppcon还贵

[Visual Studio 2022 17.1 is now available!](https://devblogs.microsoft.com/visualstudio/visual-studio-2022-17-1-is-now-available/)

[编译器信息最新动态推荐关注hellogcc公众号 本周更新 2022-02-16 第137期](https://github.com/hellogcc/osdt-weekly/blob/master/weekly-2022/2022-02-16.md)

## 文章

- [**Did you know that C++23 added Attributes on Lambda-Expressions?**](https://github.com/QuantlabFinancial/cpp_tip_of_the_week/)

```c++
constexpr auto foo = [] [[deprecated]] { };

int main() {
foo(); // operator() is deprecated
}
```

Lambda 可以标注

- [C++ 项目编译优化](https://bot-man-jl.github.io/articles/?post=2022/Cpp-Project-Compile-Optimization)

主要是利用clang的 [`-ftime-trace` 参数](https://clang.llvm.org/docs/ClangCommandLineReference.html#cmdoption-clang-ftime-trace)

我记得gcc也有一个类似的找不到了

- [C++ Templates: How to Iterate through std::tuple: std::apply and More](https://www.cppstories.com/2022/tuple-iteration-apply/)

承接上文啊,能实现遍历打印,肯定也能实现遍历调用lambda,如何实现呢?

核心代码,之前的index_sequence搬过来,另外还需要展开变参模版

for_each_tuple和之前的printtuple类似,for_each_tuple2避免难理解,主要是依赖lambda的模版能力,也是要展开变参模版

```c++
template <typename TupleT, typename Fn, std::size_t... Is>
void for_each_tuple_impl(TupleT&& tp, Fn&& fn, std::index_sequence<Is...>) {
(fn(std::get<Is>(std::forward<TupleT>(tp))), ...);
}

template <typename TupleT, typename Fn, std::size_t TupSize = std::tuple_size_v<std::remove_cvref_t<TupleT>>>
void for_each_tuple(TupleT&& tp, Fn&& fn) {
for_each_tuple_impl(std::forward<TupleT>(tp), std::forward<Fn>(fn), std::make_index_sequence<TupSize>{});
}

template <typename TupleT, typename Fn>
void for_each_tuple2(TupleT&& tp, Fn&& fn) {
std::apply
(
[&fn]<typename ...T>(T&& ...args)
{
(fn(std::forward<T>(args)), ...);
}, std::forward<TupleT>(tp)
);
}
```
- [Constant references are not always your friends](https://belaycpp.com/2022/02/15/constant-references-are-not-always-your-friends/)
虽然一般来说不需要拷贝的传参数用const T&就万事大吉,但是有些场景是不行的,比如T的设计不合理
我们要考虑T设计的问题,另外小对象,不要用const T&,比如string_view span int这种 直接传value
- [c++ execution 与 coroutine (五):异步 - 知乎 (zhihu.com)](https://zhuanlan.zhihu.com/p/441741987)
[c++ execution 与 coroutine (六):coroutine概述 - 知乎 (zhihu.com)](https://zhuanlan.zhihu.com/p/443847625)
[c++ execution 与 coroutine (七):awaiter也是sender](https://zhuanlan.zhihu.com/p/445943412)
突然得知executor进不了c++23了,哎可惜。这些概念了解一下还是可以的。抽象程度很高
- [C++ Trailing Return Types](https://www.danielsieger.com/blog/2022/01/28/cpp-trailing-return-types.html)
讨论了一下把返回值放到后面的可行性,主要原因是作者开发的库经常会遇到这个返回值类型不确定的场景,比如
```c++
template<typename A, typename B>
decltype(std::declval<A>() * std::declval<B>()) multiply(A a, B b) { return a*b; }
```

- [The 114 standard C++ algorithms. Introduction](https://itnext.io/the-114-standard-c-algorithms-introduction-2a75a2df4300)

标准库的算法,了解一下

- [C++23: Deducing this](https://www.sandordargo.com/blog/2022/02/16/deducing-this-cpp23)

考虑一种场景,成员函数修饰调用限定

```c++
void Foo::bar() & { /* ... */ }
void Foo::bar() && { /* ... */ }
void Foo::bar() const & { /* ... */ }
void Foo::bar() const && { /* ... */ }
```
后面这种场景是为了限定Foo在某些类型的场景下才能调用
有了deducing this就能简化。举个例子
```c++
template <typename T>
class OptionalNotDeducingThis {
// ...
constexpr T* operator->() {
return addressof(this->m_value);
}
constexpr T const*
operator->() const {
return addressof(this->m_value);
}
// ...
};
template <typename T>
class OptionalDeducingThis {
// ...
template <typename Self>
constexpr auto operator->(this Self&& self) {
return addressof(self.m_value);
}
// ...
};
```

this Self来决定auto,所以你要const就 T* const,你不const的就T*

- [Faster integer formatting - James Anhalt (jeaiii)’s algorithm](https://jk-jeon.github.io/posts/2022/02/jeaiii-algorithm/)

一个证书序列化成字符串的算法(itoa)比fmt库内部的算法还要快,不过fmt作者没有考虑使用这个算法。

这里简单介绍一下

最简单的写法

```c++
char* itoa_naive(std::uint32_t n, char* buffer) {
char temp[10];
char* ptr = temp + sizeof(temp) - 1;
while (n >= 10) {
*ptr = char('0' + (n % 10));
n /= 10;
--ptr;
}
*ptr = char('0' + n);
auto length = temp + sizeof(temp) - ptr;
std::memcpy(buffer, ptr, length);
return buffer + length;
}

```
把整数序列化到temp数组,再拷贝出去,buf是10是因为int32就那么大
显然循环除10很慢,我们可以考虑减少循环次数,然后考虑除100
然后直接把余数给算好
首先想到的优化就是查表写数,而不是计算
```c++
static constexpr char radix_100_table[] = {
'0', '0', '0', '1', '0', '2', '0', '3', '0', '4',
'0', '5', '0', '6', '0', '7', '0', '8', '0', '9',
'1', '0', '1', '1', '1', '2', '1', '3', '1', '4',
'1', '5', '1', '6', '1', '7', '1', '8', '1', '9',
'2', '0', '2', '1', '2', '2', '2', '3', '2', '4',
'2', '5', '2', '6', '2', '7', '2', '8', '2', '9',
'3', '0', '3', '1', '3', '2', '3', '3', '3', '4',
'3', '5', '3', '6', '3', '7', '3', '8', '3', '9',
'4', '0', '4', '1', '4', '2', '4', '3', '4', '4',
'4', '5', '4', '6', '4', '7', '4', '8', '4', '9',
'5', '0', '5', '1', '5', '2', '5', '3', '5', '4',
'5', '5', '5', '6', '5', '7', '5', '8', '5', '9',
'6', '0', '6', '1', '6', '2', '6', '3', '6', '4',
'6', '5', '6', '6', '6', '7', '6', '8', '6', '9',
'7', '0', '7', '1', '7', '2', '7', '3', '7', '4',
'7', '5', '7', '6', '7', '7', '7', '8', '7', '9',
'8', '0', '8', '1', '8', '2', '8', '3', '8', '4',
'8', '5', '8', '6', '8', '7', '8', '8', '8', '9',
'9', '0', '9', '1', '9', '2', '9', '3', '9', '4',
'9', '5', '9', '6', '9', '7', '9', '8', '9', '9'
};
char* itoa_two_digits_per_div(std::uint32_t n, char* buffer) {
char temp[8];
char* ptr = temp + sizeof(temp);
while (n >= 100) {
ptr -= 2;
std::memcpy(ptr, radix_100_table + (n % 100) * 2, 2);
n /= 100;
}
if (n >= 10) {
std::memcpy(buffer, radix_100_table + n * 2, 2);
buffer += 2;
}
else {
buffer[0] = char('0' + n);
buffer += 1;
}
auto remaining_length = temp + sizeof(temp) - ptr;
std::memcpy(buffer, ptr, remaining_length);
return buffer + remaining_length;
}
```

说实话这块我就看不懂了,后面更难了。这里标记个TODO,有时间研究一下

- [Algorithms for Modern Hardware](https://en.algorithmica.org/hpc/)

作者的一些优化经验,我看lamire老哥也关注了。写的很有噱头

> - 2x faster GCD (compared to `std::gcd`)
> - 8-15x faster binary search (compared to `std::lower_bound`)
> - 7x faster segment trees
> - 5x faster hash tables (compared to `std::unordered_map`)
> - ~~?x faster popcount~~
> - 2x faster parsing series of integers (compared to `scanf`)
> - ?x faster sorting (compared to `std::sort`)
> - 2x faster sum (compared to `std::accumulate`)
> - 10x faster array searching (compared to `std::find`)
> - 100x faster matrix multiplication (compared to “for-for-for”)
> - optimal word-size integer factorization (~0.4ms per 60-bit integer)
> - optimal Karatsuba Algorithm
> - optimal FFT
> - argmin at the speed of memory
文章很长一时半会看不完,这里先标记TODO了

- [Projections are Function Adaptors](https://brevzin.github.io/c++/2022/02/13/projections-function-adaptors/)

```c++
struct Person {
std::string first;
std::string last;
};

std::vector<Person> people = { /* ... */ };
std::vector<std::string> r_names;
std::ranges::copy_if(
people,
std::back_inserter(r_names),
[](std::string const& s) { return s[0] == 'R'; },
&Person::last);

```
```c++
std::ranges::copy_if(
people | std::views::transform(&Person::last),
std::back_inserter(r_names),
[](std::string const& s) { return s[0] == 'R'; });
```

看懂这两段代码的区别了吗,第一段代码不工作,因为

## 视频

- [C++ Weekly - Ep 311 - ++i vs i++ ](https://www.youtube.com/watch?v=ObVRSNvGitE)

没啥说的

- [SIMD algorithms](https://www.youtube.com/watch?v=U1e_k8xmwR0&list=PLYCMvilhmuPEM8DUvY6Wg_jaSFHpmlSBD)

有时间可以看一下。simd感觉早晚得了解,躲不开

这里标记一个TODO,后面看了总结一下

## 开源项目需要人手

- [asteria](https://github.com/lhmouse/asteria) 一个脚本语言,可嵌入,长期找人,希望胖友们帮帮忙,也可以加群384042845和作者对线
- [pika](https://github.com/OpenAtomFoundation/pika) 一个nosql 存储, redis over rocksdb,非常需要人贡献代码胖友们, 感兴趣的欢迎加群294254078前来对线

## 新项目介绍/版本更新

- [meta.hpp](https://github.com/blackmatov/meta.hpp) c++20反射库
- [log.c](https://github.com/rxi/log.c)一个log库,c的



---

看到这里或许你有建议或者疑问或者指出错误,请留言评论! 多谢! 你的评论非常重要!也可以帮忙点赞收藏转发!多谢支持!

[本文永久链接](https://wanghenshui.github.io/cppweeklynews/posts/050.html)

0 comments on commit 87fd736

Please sign in to comment.