C++ 中文周刊 2024-07-06 第163期

2024-07-30 15:24:00 浏览数 (2)

本期文章由 HMY lhmouse赞助

资讯

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

最近陆陆续续又有很多c 26 St Louis参会报告出来,这里列一下

https://mpusz.github.io/mp-units/latest/blog/2024/07/02/report-from-the-st-louis-2024-iso-c-committee-meeting/

https://quuxplusone.github.io/blog/2024/06/30/st-louis-trip-report/

https://herbsutter.com/2024/07/02/trip-report-summer-iso-c-standards-meeting-st-louis-mo-usa/

https://www.reddit.com/r/cpp/comments/1dwc7f2/202406_st_louis_iso_c_committee_trip_report/

另外上周也介绍了mick的报告

另外Ykiko也写了一个 St. Louis WG21 会议回顾

知乎原文 https://zhuanlan.zhihu.com/p/706509748

文章

Can you change state in a const function in C ? Why? How?

https://bytesandlogs.me/can-you-change-state-in-const-function-in-cpp/

const_cast

Cooperative Interruption of a Thread in C 20

https://www.modernescpp.com/index.php/cooperative-interruption-of-a-thread-in-c20/

介绍stop_token,其实就是塞了个状态回调,规范化了一下 直接看代码

代码语言:javascript复制
#include <chrono>
#include <iostream>
#include <thread>
#include <vector>

usingnamespace::std::literals;

auto func =[](std::stop_token stoken){// (1)
int counter{0};
auto thread_id = std::this_thread::get_id();
std::stop_callback callBack(stoken, [&counter, thread_id] {  // (2)
            std::cout << "Thread id: " << thread_id 
                      << "; counter: " << counter << 'n';
        });
while(counter <10){
            std::this_thread::sleep_for(0.2s);
  counter;
}
};

int main() {
std::vector<std::jthread> vecThreads(10);
for(auto& thr: vecThreads) thr = std::jthread(func);

    std::this_thread::sleep_for(1s);// (3)    
for(auto& thr: vecThreads) thr.request_stop();// (4)
}

A 16-byte std::function implementation

https://www.reddit.com/r/cpp/comments/1dwkgue/a_16byte_stdfunction_implementation/

直接贴代码吧

代码语言:javascript复制
template<typename T>
struct sfunc;

template<typename R, typename ...Args>
struct sfunc<R(Args...)> {
    struct lambda_handler_result {
        void* funcs[3];
    };

    enum class tag {
        free,
        copy,
        call 
    };

    lambda_handler_result (*lambda_handler)(void*, void**) {nullptr};
    void* lambda {nullptr};

    template<typename F>
    sfunc(F f) { *this = f;}
    sfunc() {}
    sfunc(const sfunc& f) { *this = f; }
    sfunc(sfunc&& f) { *this = f; }

    sfunc& operator = (sfunc&& f) {
        if(&f == this){
            return *this;
        }
        lambda_handler = f.lambda_handler;
        lambda = f.lambda;
        f.lambda_handler = nullptr;
        f.lambda = nullptr;
        return *this;
    }

    void free_lambda() {
        if(lambda_handler) {
            auto ff {lambda_handler(lambda, nullptr).funcs[(int)tag::free]};
            if(ff){
                ((void(*)(void*))ff)(lambda); 
            }
        }
        lambda = nullptr;
    }

    sfunc& operator = (const sfunc& f) {
        if(&f == this) {
            return *this;
        }
        free_lambda();
        lambda_handler = f.lambda_handler;
        if(f.lambda) {
            auto ff {lambda_handler(lambda, nullptr).funcs[(int)tag::copy]};
            if(ff) {
                ((void(*)(void*, void**))ff)(f.lambda, &lambda); 
            } else { 
                lambda = f.lambda;
            }
        }
        return *this;
    }

    template<typename ...>
    struct is_function_pointer;

    template<typename T>
    struct is_function_pointer<T> {
        static constexpr bool value {false};
    };

    template<typename T, typename ...Ts>
    struct is_function_pointer<T(*)(Ts...)> {
        static constexpr bool value {true};
    };

    template<typename F>
    auto operator = (F f) {
        if constexpr(is_function_pointer<F>::value == true) {
            free_lambda();
            lambda = (void*)f;
            lambda_handler = [](void* l, void**) {
                return lambda_handler_result{{nullptr, nullptr, (void*) [](void* l, Args... args) {
                    auto& f {*(F)l};
                    return f(forward<Args>(args)...);
                }}};
            };
        } else {
            free_lambda();
            lambda = {new F{f}};
            lambda_handler = [](void* d, void** v) {
                return lambda_handler_result{{(void*)[](void*d){ delete (F*)d;},
                                          (void*)[](void*d, void** v){ *v = new F{*((F*)d)};},
                                          (void*)[](void* l, Args... args)
                                          {
                                              auto& f {*(F*)l};
                                              return f(forward<Args>(args)...);
                                          }}};
            };
        }
    }

    inline R operator()(Args... args) {
        return ((R(*)(void*, Args...))lambda_handler(nullptr, nullptr).funcs[(int)tag::call])(lambda, forward<Args>(args)...);
    }

    ~sfunc() { free_lambda(); }
};

没SSO

A Type for Overload Set

https://biowpn.github.io/bioweapon/2024/07/02/a-type-for-overload-set.html

函数没有类型,直接赋值是不可以的

代码语言:javascript复制
void f(int);
void f(int, int);
// `f` is an overload set with 2 members

auto g = f;// error! cannot deduce the type of `g`

// This is because:
using FF =decltype(f);// error! overload set has not type
std::invocable<int>auto g = f;// error! cannot deduce the type of `g`

// bind invoke也不行,他们要接受对象

而lambda有类型,即使这个类型看不到,那么就可以封装一层

代码语言:javascript复制
#include <cassert>
#include <utility>

int g(int x) { return x   1; }
int g(int x, int y) { assert(false); }

class MyClass {
public:
    int f(int x) { return x   1; }
    int f(int x, int y) { assert(false); }
};

#define OVERLOAD(...) [&](auto &&... args) -> decltype(auto) { 
    return __VA_ARGS__(std::forward<decltype(args)>(args)...); 
}

int main(int argc, char *argv[]) {
    assert(OVERLOAD(g)(5) == 6);
    MyClass obj;
    assert(OVERLOAD(obj.f)(5) == 6);
  return 0;
}

godbolt https://godbolt.org/z/zrcsaG9xE

P3312就是这盘饺子 https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2024/p3312r0.pdf

Compile-time JSON deserialization in C https://medium.com/@abdulgh/compile-time-json-deserialization-in-c-1e3d41a73628

没看懂

Beating NumPy's matrix multiplication in 150 lines of C code https://salykova.github.io/matmul-cpu

代码在这 https://github.com/salykova/matmul.c

感觉不是很靠谱,影响因素太多了

视频

C Weekly - Ep 435 - Easy GPU Programming With AdaptiveCpp (68x Faster!)

https://www.youtube.com/watch?v=ImM7f5IQOaw&ab_channel=C++WeeklyWithJasonTurner

介绍opensycl的 https://github.com/AdaptiveCpp/AdaptiveCpp

自己看吧,我不是业内,不了解

Björn Fahller: Cache friendly data functional ranges = ❤️

https://www.youtube.com/watch?v=3Rk-zSzloL4&ab_channel=SwedenCpp

https://github.com/rollbear/columnist 他这个SOA库还挺有意思的

0 人点赞