c++的数组作为函数形参的退化问题

在项目过程中,因为涉及到用c#调用c++的dll,其中有一个定义好的数组,想转为c++中的vector,将数组作为形参传到函数内部后,需要遍历每个数组,代码如下:


可以看到,在函数内部需要知道数组的长度,也就是元素个数,但使用了网上说的sizeof函数,始终求出来等于8,仔细查阅资料才发现这里存在一个数组作为函数参数的退化问题。即当数组被初始化后,在不被函数调用的情况下,可以用sizeof求出正确的数组长度,一旦作为函数参数传递到函数内部,该参数就退化为一个指针,对该指针求sizeof则始终是一个指针的长度,而不是数组的长度(我能吐槽这个奇葩的隐含规则么?这对于代码重构可是一个灾难性的后果)

       对于c++老手高手高高手来说,这可能是一个基础性的常识问题,但对于新人来讲,绝对会发出“人生苦短,远离c渣渣”的感叹。幸好网友的智慧是无穷的,随手一查,就发现很多高手已经给出了解决方案。

      1、把数组长度作为另外一个参数传进去。(好吧,也就多一个参数不是么)

     2、自定义数组模板。(既然需要造轮子,那就只好造一个了),具体如下:

参考网友gaopengtttt的文章:C++ 简单实现数组类泛型编程示例

  1. 模板类实现:
  2. /*************************************************************************
  3.     > File Name: arra.cpp
  4.     > Author: gaopeng QQ:22389860 all right reserved
  5.     > Mail: gaopp_200217@163.com
  6.     > Created Time: Mon 10 Apr 2017 08:28:01 AM CST
  7.  ************************************************************************/

  8. #include<iostream>
  9. #include <stdlib.h>
  10.  #include <string.h>
  11. using namespace std;


  12. template <typename T>
  13. class myarray
  14. {
  15.         private:
  16.                 T* array;
  17.                 unsigned int lenth;
  18.         public:
  19.                 myarray();
  20.                 myarray(unsigned int len);
  21.                 myarray(const myarray& a);
  22.                 myarray& operator=(const myarray& b);
  23.                 T& operator[](int ind);
  24.                 ~myarray();
  25. };




  26. template <typename T>
  27. myarray<T>::~myarray()
  28. {
  29.         if(this->array != NULL)
  30.         {
  31.                 delete [] this->array;
  32.                 this->array = NULL;
  33.         }

  34. }


  35. template <typename T>
  36. myarray<T>::myarray()
  37. {
  38.         this->array = NULL;
  39.         this->lenth = 0;
  40. }

  41. template <typename T>
  42. myarray<T>::myarray(unsigned int len)
  43. {
  44.         this->array = new T[len];
  45.         this->lenth = len;
  46.         memset(this->array,0,sizeof(T)*len);
  47. }
  48. template <typename T>
  49. myarray<T>::myarray(const myarray<T>& a)
  50. {
  51.         int i;
  52.         this->lenth = a.lenth;
  53.         this->array = new T[a.lenth];
  54.         memset(this->array,0,sizeof(T)*a.lenth);
  55.         for(i=0;i<a.lenth;i++)
  56.         {
  57.                 *(this->array+i) = *(a.array+i);
  58.         }
  59. }

  60. template <typename T>
  61. myarray<T>& myarray<T>::operator=(const myarray<T>& a)
  62. {
  63.         if(this->array != NULL)
  64.         {
  65.                 delete [] this->array;//调用类的析构函数不能用free
  66.                 this->array = NULL;
  67.         }
  68.         this->array = new T[a.lenth];
  69.         this->lenth = a.lenth;

  70.         for(int i=0;i<a.lenth;i++)
  71.         {
  72.                 *(this->array+i) = *(a.array+i);//元素对象复制调用对象的=操作符重载
  73.         }

  74.         return *this;
  75. }

  76. template <typename T>
  77. T& myarray<T>::operator[](int ind)
  78. {
  79.         if(ind>=this->lenth)
  80.         {
  81.                 exit(10);
  82.         }
  83.         return *(this->array+ind);
  84. }

  1. 测试
  2. /*************************************************************************
  3.     > File Name: main.cpp
  4.     > Author: gaopeng QQ:22389860 all right reserved
  5.     > Mail: gaopp_200217@163.com
  6.     > Created Time: Mon 10 Apr 2017 08:31:57 AM CST
  7.  ************************************************************************/

  8. #include<iostream>
  9. #include<stdlib.h>
  10. #include<string.h>
  11. #include"arra.cpp"

  12. using namespace std;

  13. class test
  14. {
  15.         private:
  16.                 int a;
  17.                 int b;
  18.                 char* myc;
  19.         public:
  20.                 test()
  21.                 {
  22.                         a = 0;
  23.                         b = 0;
  24.                         myc = NULL;
  25.                 }
  26.                 test(const test& a)
  27.                 {
  28.                         this->= a.a;
  29.                         this->= a.b;
  30.                         this->myc = (char*)calloc(strlen(a.myc)+1,0);
  31.                         strcpy(this->myc,a.myc);
  32.                 }


  33.                 friend ostream& operator<<(ostream& out,test& a)
  34.                 {
  35.                         out<<a.a<<endl;
  36.                         out<<a.b<<endl;
  37.                         cout<<a.myc;
  38.                         return out;
  39.                 }
  40.                 ~test()
  41.                 {
  42.                         if(myc != NULL)
  43.                         {
  44.                                 free(myc);
  45.                                 myc = NULL;
  46.                         }
  47.                 }

  48.                 test& operator=(const test& a)
  49.                 {
  50.                         if(this->myc != NULL)
  51.                         {
  52.                                 free(this->myc);
  53.                                 this->myc = NULL;
  54.                         }
  55.                         this->= a.a;
  56.                         this->= a.b;
  57.                         this->myc = (char*)calloc(strlen(a.myc)+1,0);
  58.                         strcpy(this->myc,a.myc);
  59.                         return *this;
  60.                 }

  61.                 test& operator=(const char* a)
  62.                 {
  63.                         if(this->myc != NULL)
  64.                         {
  65.                                 free(this->myc);
  66.                                 this->myc = NULL;
  67.                         }
  68.                         if(== NULL)
  69.                         {
  70.                                 this->myc = (char*)calloc(1,0);
  71.                                 return *this;
  72.                         }

  73.                         this->myc = (char*)calloc(strlen(a)+1,0);
  74.                         strcpy(this->myc,a);
  75.                         return *this;
  76.                 }

  77. };



  78. int main()
  79. {
  80.         myarray<test> a(3); //测试class类数组
  81.         a[0] = "asdasd";
  82.         a[1] = "test";
  83.         a[2] = "kkkk";

  84.         myarray<int> b(3); //测试int数组

  85.         b[0] = 1;
  86.         b[1] = 2;
  87.         b[2] = 3;

  88.         myarray<char> c(3); //测试char数组

  89.         c[0] = 'a';
  90.         c[1] = 'b';
  91.         c[2] = 'c';

  92.         myarray<test> d = a;//测试myarray拷贝构造函数

  93.         for(int i=0;i<3;i++)
  94.         {
  95.                 cout<<a[i]<<endl;
  96.                 cout<<d[i]<<endl;
  97.         }

  98.         for(int i=0;i<3;i++)
  99.         {
  100.                 cout<<b[i]<<endl;
  101.         }
  102.         for(int i=0;i<3;i++)
  103.         {
  104.                  cout<<c[i]<<endl;
  105.         }

  106. }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值