《C++ Primer Plus》第五版 程序清单4.22 delete.cpp

//程序清单4.22 delete.cpp
#include 
#include 

using namespace std;
char * getname(void);

int main()
{
    char * name;

    name = getname();
    cout << name << " at " << (int *)name << endl;
    delete [] name;

    name = getname();
    cout << name << " at " << (int *)name << endl;
    delete [] name;

    return 0;
}

char * getname()
{
    char temp[80];
    cout << "Enter last name: ";
    cin >> temp;
    char * pn = new char[strlen(temp) + 1];
    strcpy(pn, temp);

    return pn;
}

运行结果:

Enter last name: philip
philip at 0x3d65a8
Enter last name: john
john at 0x3d65a8

Process returned 0 (0x0)   execution time : 18.201 s
Press any key to continue.

分析:

  1. 该程序的目的是为了节省内存。首先将字符串读入到一个大型的临时数组中,然后用new[]创建一个刚好能够存储该输入字符串的内存块,并返回一个指向该内存块的指针。当getname()运行完,存储临时数组的栈中的内存将被自动释放,因此分配的内存即为刚好可以存储字符串的内存,节约了内存。
  2. 因为指针ps指向的内存是由new分配的数组,而指针name=ps,因此指针name指向的内存也是由new分配的数组,所以在delete该内存时需要使用delete[] name
  3. 在语句cout << name << " at " << (int *)name << endl;一般来说,如果给cout提供一个指针,它将打印地址。但如果指针的类型为char ,则cout将显示指向的字符串。如果要显示的是字符串的地址,则必须将这种地址强制转化为另一种指针类型,例如(int )。
  4. 对于字符数组,它的结束符是系统默认给加的空字符”\0”,目的是,在使用该字符数组时,其实系统只是记住了指向该字符数组首元素的指针的值,然后顺序打印,直到遇到空字符”\0”。因此,我们在将temp[]复制到pn时,对pn申请的地址长度为strlen(temp) + 1。测试:char a[10] = "ab\0cd"; cout << a << endl; // 打印结果为ab
  5. 关于strlen()和sizeof()
    char str[20]=”0123456789搜索”;
    int a=strlen(str); //a=10;
    int b=sizeof(str); //而b=20;
  6. 该程序存在的问题:将new和delete放在不同的函数中通常并不是个好办法,因为这样很容易忘记使用delete。该例子中这样做只是为了方便。

.

你可能感兴趣的:(C++)