当前位置:   article > 正文

String类的深浅拷贝以及写时拷贝_kotlin怎么深拷贝一个string

kotlin怎么深拷贝一个string

       浅拷贝:类的所有对象的成员变量指针指向同一块空间(成员变量是开辟在堆区的),类默认的拷贝构造函数和赋值运算符重载都采用浅拷贝,如果不加以处理,当析构函数对空间进行释放时,就会出现堆区空间二次释放的问题。但是浅拷贝也可以起到节省内存空间的作用,这里就需要利用静态的成员变量来进行对象计数,析构函数中 对计数进行判断,如果只剩下一个对象再进行真正的析构操作。

       深拷贝:对于拷贝构造和赋值运算符重载重新实现,赋值时每次都要开辟新空间。注意赋值运算符重载中,需要进行旧空间释放(不然会造成内存泄漏)和是否是自身赋值的判断。

      所有对象都只是访问数据而不修改,浅拷贝是可以的,但是当有对象要进行数据修改时就应该按深拷贝来实现。深拷贝和浅拷贝(对象计数)的实现:这种所有的对象都进行统一引用计数的方式是错误的,比如s3应当和s1、s2没有关联,而且这里的成员变量一改俱改。

  1. #define _CRT_SECURE_NO_WARNINGS
  2. #include<iostream>
  3. #include<vld.h>
  4. using namespace std;
  5. class String
  6. {
  7. friend ostream& operator<<(ostream& cout, const String& s);
  8. public:
  9. String(const char* str="")
  10. {
  11. this->m_data = new char[strlen(str) + 1];
  12. strcpy(m_data, str);
  13. this->m_count++;
  14. }
  15. String(const String& s)
  16. {
  17. /* this->m_data = new char[strlen(s.m_data)+1];
  18. strcpy(this->m_data, s.m_data);*/
  19. this->m_data = s.m_data;
  20. this->m_count++;
  21. }
  22. String& operator=(const String& s)
  23. {
  24. if (this != &s)
  25. {
  26. this->m_data = s.m_data;
  27. /*delete this->m_data;
  28. this->m_data = new char[strlen(s.m_data) + 1];
  29. strcpy(this->m_data, s.m_data);*/
  30. this->m_count++;
  31. }
  32. return *this;
  33. }
  34. ~String()
  35. {
  36. if (--this->m_count == 0)//浅拷贝和浅赋值
  37. {
  38. delete[] m_data;
  39. m_data = nullptr;
  40. }
  41. }
  42. public:
  43. void do_uper(char* p)
  44. {
  45. while (*p != '\0')
  46. {
  47. if (*p >= 'a' && *p <= 'z')
  48. {
  49. *p -= 32;
  50. }
  51. p++;
  52. }
  53. }
  54. void to_upper()//写时拷贝,只有在修改对象成员变量时才开辟新空间
  55. {
  56. char* p=NULL;
  57. if (this->m_count > 1)
  58. {
  59. char* tmp = new char [strlen(m_data) + 1];
  60. strcpy(tmp, this->m_data);
  61. this->m_data = tmp;
  62. p = tmp;
  63. this->m_count--;
  64. }
  65. else
  66. {
  67. p = this->m_data;
  68. }
  69. do_uper(p);
  70. }
  71. private:
  72. char* m_data;
  73. static int m_count;
  74. };
  75. int String::m_count = 0;
  76. ostream& operator<<(ostream& cout, const String& s)
  77. {
  78. cout << s.m_data << endl;
  79. return cout;
  80. }
  81. void test01()
  82. {
  83. String s("abc");
  84. }
  85. void test02()
  86. {
  87. String s1("abc");
  88. String s2 = s1;
  89. String s3;
  90. s3 = s1;
  91. cout << s1;
  92. cout << s2;
  93. cout << s3;
  94. }
  95. void test03()
  96. {
  97. String s1("abc");
  98. String s2 = s1;
  99. String s3("xyz");
  100. s1.to_upper();
  101. cout << s1;
  102. cout << s2;
  103. }
  104. int main()
  105. {
  106. //test01();
  107. test03();
  108. system("pause");
  109. return 0;
  110. }

String类的写时拷贝:

  1. #define _CRT_SECURE_NO_WARNINGS
  2. #include<iostream>
  3. #include<assert.h>
  4. #include<vld.h>
  5. using namespace std;
  6. //#define DISPLAY
  7. class String_rep
  8. {
  9. friend class String;
  10. public:
  11. String_rep(const char* str = "") :m_count(0)
  12. {
  13. #ifdef DISPLAY
  14. cout << "Creat String_Rep Obj" << endl;
  15. #endif
  16. this->m_data = new char[strlen(str) + 1];
  17. strcpy(m_data, str);
  18. }
  19. String_rep(const String_rep& rep)
  20. {
  21. this->m_data = rep.m_data;//浅拷贝
  22. //increament();
  23. }
  24. String_rep& operator=(const String_rep& rep)
  25. {
  26. if (this != &rep)
  27. {
  28. this->m_data = rep.m_data;
  29. //increament();
  30. }
  31. return *this;
  32. }
  33. char* getData()
  34. {
  35. return m_data;
  36. }
  37. ~String_rep()
  38. {
  39. #ifdef DISPLAY
  40. cout << "Free String_Rep Obj" << endl;
  41. #endif
  42. delete[] this->m_data;
  43. this->m_data = NULL;
  44. }
  45. void increament()
  46. {
  47. this->m_count++;
  48. }
  49. void decreament()
  50. {
  51. if (--m_count == 0)
  52. {
  53. delete this;//自杀式释放
  54. }
  55. }
  56. private:
  57. char* m_data;
  58. int m_count;
  59. };
  60. class String
  61. {
  62. friend ostream& operator<<(ostream& cout, const String& s);
  63. public:
  64. String(const char* str = "") :pn(new String_rep(str))
  65. {
  66. #ifdef DISPLAY
  67. cout << "Creat String Obj" << endl;
  68. #endif
  69. pn->increament();
  70. }
  71. String(const String& s):pn(s.pn)
  72. {
  73. pn->increament();
  74. }
  75. String& operator=(const String& s)
  76. {
  77. if (this != &s)
  78. {
  79. pn->decreament();
  80. pn = s.pn;
  81. pn->increament();
  82. }
  83. return *this;
  84. }
  85. void to_upper()
  86. {
  87. String_rep* new_pn = new String_rep(pn->m_data);
  88. pn->decreament();
  89. pn = new_pn;
  90. pn->increament();
  91. char* p = pn->m_data;
  92. while (*p != '\0')
  93. {
  94. if (*p >= 'a' && *p <= 'z')
  95. *p -= 32;
  96. p++;
  97. }
  98. }
  99. ~String()
  100. {
  101. #ifdef DISPLAY
  102. cout << "Free String Obj" << endl;
  103. #endif
  104. pn->decreament();
  105. }
  106. private:
  107. String_rep* pn;
  108. };
  109. ostream& operator<<(ostream& cout, const String& s)
  110. {
  111. cout << s.pn->getData() << endl;
  112. return cout;
  113. }
  114. void test01()
  115. {
  116. String s1("abc");
  117. //{
  118. // String s1 = s;
  119. //}
  120. String s2 = s1;
  121. String s3("xyz");
  122. }
  123. void test02()
  124. {
  125. String s("abc");
  126. String s1("xyz");
  127. String s2 = s1;
  128. s = s1;
  129. }
  130. void test03()
  131. {
  132. String s1("abc");
  133. String s2 = s1;
  134. String s3 = s2;
  135. cout <<"s1="<< s1;
  136. cout <<"s2="<<s2;
  137. s1.to_upper();
  138. cout <<"s1="<< s1;
  139. cout <<"s2="<< s2;
  140. }
  141. int main()
  142. {
  143. //test01();
  144. test03();
  145. system("pause");
  146. return 0;
  147. }

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/不正经/article/detail/501749
推荐阅读
相关标签
  

闽ICP备14008679号