前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >C++ 动态新闻推送 第53期

C++ 动态新闻推送 第53期

作者头像
王很水
发布2022-03-15 14:08:16
1960
发布2022-03-15 14:08:16
举报
文章被收录于专栏:C++ 动态新闻推送

C++ 动态新闻推送 第53期

reddit/hackernews/lobsters/meetingcpp摘抄一些c++动态

资讯

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

编译器信息最新动态推荐关注hellogcc公众号 本周更新 2022-03-09 第140期

文章

一个async对应一个future,别共用一个future,会阻塞

代码语言:javascript
复制
using my_map = unordered_map<{
  .key = type<int>, .value = type<std::string>,
  .allocator = type< my_allocator< std::pair<const int, std::string > > >
}>;

注意这个用法,说实话还是挺别扭。能省几行代码

有些类型是可以拷贝但不能比较的,比如function

STL中还有哪个组件类似?

代码语言:javascript
复制
constexpr std::monostate m;
static_assert(m == m);

std::monostate按理说就是个tag类型,比较没有意义,但是这里确实可以比较,本身有value语义

再比如

代码语言:javascript
复制
constexpr std::nullopt_t n;
bool b = (n == n);  // Error: does not compile!

nullopt明显没有value语义

通过把输出定向到 /dev/full 可以看到错误硬件错误,这是一个测试的好手段,可以判断如果调用了硬件接口报错是不是真的处理了错误码

代码语言:javascript
复制
$ echo "Hello World!" > /dev/full
bash: echo: write error: No space left on device
$ echo $?
1

但是c/c++是没有处理的

代码语言:javascript
复制
cat hello.c
/* Hello World in C, Ansi-style */

#include <stdio.h>
#include <stdlib.h>

int main(void)
{
  puts("Hello World!");
  return EXIT_SUCCESS;
}

gcc hello.c -o hello
./hello > /dev/full
echo $?
1

strace -etrace=write ./hello > /dev/full
write(1, "Hello World!\n", 13)          = -1 ENOSPC (No space left on device)
+++ exited with 0 +++

作者测试了其他语言,汇总了个表格,有些处理了,有些没处理。这里就不介绍了

用模板包装

代码语言:javascript
复制
class Car {
public:
  ~Car() = default;
  void startEngine() {
    // some implementation
  }
  
  int getTrunkSize() const {
    // some implementation
  }
  
  void addFuel(double quantity) {
    // some implementation
  }
};

class MockCar {
public:
  MOCK_METHOD(void, startEngine, (), ());
  MOCK_METHOD(int, getTrunkSize, (), (const));
  MOCK_METHOD(void, addFuel, (double quantity), ());
};

template <typename CarImpl>
class CarWrapper {
public:
  CarWrapper(C carImpl): _carImpl(carImpl) {}

  void startEngine() {
    _carImpl.startEngine();
  }
  
  int getTrunkSize() const {
    return _carImpl.getTrunkSize();
  }
  
  void addFuel(double quantity) {
    _carImpl.addFuel();
  } 
private:
  CarImpl _carImpl;
}


	

CarWrapper<MockedCar> c;

另外gmock也有新组件

代码语言:javascript
复制
TEST(CarMockTest, testStatementOrder) {
  ::testing::NiceMock<MockCar> c;
  EXPECT_CALL(c, startEngine()).Times(1);
  c.startEngine();
}

可以看googlemock/docs/CookBook.md 了解更多

经典循环展开,SWAR SIMD过程,具体的推导过程可以看原文,我这里直接贴代码了

代码语言:javascript
复制
union Pixel
{
    uint8_t c[4]; // four channels: red, green, blue, alpha
    uint32_t v;   // full pixel value as a 32-bit integer
};

void darken(Pixel* first, Pixel* last, int darkness)
{
  int lightness = 256 - darkness;
  for (; first < last; ++first) {
    for (int i = 0; i < 3; ++i) {
      first->c[i] = (uint8_t)(first->c[i] * lightness / 256);
    }
  }
}

//展开
void darken(Pixel* first, Pixel* last, int darkness)
{
  int lightness = 256 - darkness;
  for (; first < last; ++first) {
    first->c[0] = (uint8_t)(first->c[0] * lightness / 256);
    first->c[1] = (uint8_t)(first->c[1] * lightness / 256);
    first->c[2] = (uint8_t)(first->c[2] * lightness / 256);
  }
}

//算法拆解,省掉除法, SWAR

void darken(Pixel* first, Pixel* last, int darkness)
{
  int factor = darkness / 8;
  for (; first < last; ++first) {
    uint32_t v = first->v;
    uint32_t fields = (v & 0xFF) |
                     ((v & 0xFF00) << 2) |
                     ((v & 0xFF0000) << 4);
    fields *= factor;
    fields += pack_fields(31, 31, 31);
    uint32_t diff = ((fields >> 5) & 0x1F) |
                    ((fields >> 7) & 0x1F00) |
                    ((fields >> 9) & 0x1F0000) |
    first->v = v - diff;
  }
}

//SIMD改写

void darken(Pixel* first, Pixel* last, int darkness)
{
  int lightness = 256 - darkness;
  auto lightness128 = _mm_set_epi16(
        256, lightness, lightness, lightness,
        256, lightness, lightness, lightness);
  void* end = last;
  for (auto pixels = (__m128i*)first; pixels < end; pixels++) {
    auto val = _mm_loadu_si128(pixels);
    auto vlo = _mm_unpacklo_epi8(val, _mm_setzero_si128());
    vlo = _mm_mullo_epi16(vlo, alpha128);
    vlo = _mm_srli_epi16(vlo, 8);
    auto vhi = _mm_unpackhi_epi8(val, _mm_setzero_si128());
    vhi = _mm_mullo_epi16(vhi, alpha128);
    vhi = _mm_srli_epi16(vhi, 8);
    val = _mm_packus_epi16(vlo, vhi);
    _mm_storeu_si128(pixels, val);
  }
}

不太懂,windows平台的,这里标记个TODO

视频

除了放在模板参数里,还可以这样

代码语言:javascript
复制
consteval auto as_constant(auto value) { return value;}

template<typename ... Param>
consteval decltype(auto) consteval_invoke(Param && ... param) {
    return std::invoke(std::forward<Param>(param)...);
}

一般来说用不上

讲mock的

新项目介绍/版本更新

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • C++ 动态新闻推送 第53期
    • 资讯
      • 文章
        • 视频
          • 新项目介绍/版本更新
          领券
          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档