“Overload” subscript-assignment operation in c++ 14

huangapple go评论121阅读模式
英文:

"Overload" subscript-assignment operation in c++ 14

问题

问题:

我需要构建一个数组,它存储一种类型的数据,但在内存中以另一种类型的方式显示,以节省内存。只需要重载下标运算符([])。

例如,我有一个名为arr的数组,它看起来像是fp32,但实际上在内部存储的是int8
当通过arr[i]arr中读取一个值时,通过返回值重载下标运算符就可以工作。然而,当使用类似arr[i]=somevalue的语法来赋值时,由于我不能将int8_t转换为float32_t,因此无法修改内部值。

我尝试过的:

定义一个单独的方法set(unsigned int index, float32_t value)将是一个简单的解决方案,但这将需要修改与数组交互的所有其他代码,因此不受欢迎。

我考虑使用模板数据类型进行内部存储,并重载其operator=运算符。然而,在这种情况下,无法确定[]运算符的返回类型,因此我无法进一步进行。

代码

  1. // 虚拟转换函数
  2. int8_t complex_downcast(double x) {
  3. return x;
  4. }
  5. double complex_upcast(int8_t x) {
  6. return x;
  7. }
  8. // 当前结构
  9. template <typename T, unsigned int N> struct buffer {
  10. int8_t v[N];
  11. T get(int i) const {
  12. return complex_upcast(v[i]);
  13. }
  14. T operator[](int i) const {
  15. return get(i);
  16. }
  17. void set(int i, T v) {
  18. this->v[i] = complex_downcast(v);
  19. }
  20. };
  21. buffer<double, 1> buf;
  22. buf.set(0, 2.1); // 设置为2.1,转换为int8并存储
  23. std::cout << buf[0] << std::endl; // (double) 2.0000000
  24. // 希望: 通过buf[index] = value替换buf.set(index, value),需要使用complex_downcast。
英文:

Issue:

I need to construct an array that stores one type of data but appears as another type for memory saving. Only the subscript operator ([]) is required.

Say, I have an array arr that appears as fp32 but stores int8 internally:
When reading a value from arr by arr[i], overloading the subscript operator that returns by value just works. However when assigning a value with syntax like arr[i]=somevalue, as I cannot cast int8_t to float32_t with reference, I cannot modify the inside value.

What I tried:

Defining a separate method set(unsigned int index, float32_t value) would be a simple solution, but it will require modifying all other code interacting with the array, thus not favored.

I considered using a template datatype for internal storing, and overloading its operator=. However, in this case the returned type of the [] operator cannot be determined and I cannot proceed further.

Code

  1. // dummy cast functions
  2. int8_t complex_downcast(double x) {
  3. return x;
  4. }
  5. double complex_upcast(int8_t x) {
  6. return x;
  7. }
  8. // current structure
  9. template &lt;typename T, unsigned int N&gt; struct buffer {
  10. int8_t v[N];
  11. T get(int i) const {
  12. return complex_upcast(v[i]);
  13. }
  14. T operator[](int i) const {
  15. return get(i);
  16. }
  17. void set(int i, T v) {
  18. this-&gt;v[i] = complex_downcast(v);
  19. }
  20. };
  21. buffer&lt;double, 1&gt; buf;
  22. buf.set(0, 2.1); // Sets 2.1, cast to int8 and stored
  23. std::cout &lt;&lt; buf[0] &lt;&lt; std::endl; // (double) 2.0000000
  24. // Want: replace buf.set(index, value) by buf[index] = value, where complex_downcast is required.

答案1

得分: 5

你需要做的是让数组类重载operator[]来返回一个代理对象,然后让代理对象重载operator=用于写操作,重载operator T用于读操作。然后你的代理对象的操作可以根据需要进行定义。

可以尝试像这样实现:

  1. template <typename T, unsigned int N> struct buffer {
  2. int8_t v[N];
  3. struct proxy {
  4. int8_t *elem;
  5. proxy& operator=(T value) {
  6. // 根据需要进行操作...
  7. *elem = static_cast<T>(value);
  8. return *this;
  9. }
  10. operator T() const {
  11. // 根据需要进行操作...
  12. return static_cast<T>(*elem);
  13. }
  14. };
  15. proxy operator[](int i) {
  16. return proxy{ &v[i] };
  17. }
  18. };

在线演示

英文:

What you need to do is have the array class overload the operator[] to return a proxy object, and then have the proxy overload operator= for writing and operator T for reading. Then your proxy's operators can do whatever you want.

Try something like this:

  1. template &lt;typename T, unsigned int N&gt; struct buffer {
  2. int8_t v[N];
  3. struct proxy {
  4. int8_t *elem;
  5. proxy&amp; operator=(T value) {
  6. // whatever you need...
  7. *elem = static_cast&lt;T&gt;(value);
  8. return *this;
  9. }
  10. operator T() const {
  11. // whatever you need...
  12. return static_cast&lt;T&gt;(*elem);
  13. }
  14. };
  15. proxy operator[](int i) {
  16. return proxy{ &amp;v[i]; };
  17. }
  18. };

Online Demo

huangapple
  • 本文由 发表于 2023年7月23日 21:38:05
  • 转载请务必保留本文链接:https://go.coder-hub.com/76748532.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定