careercup-C和C++ 13.8

简介: 13.8 编写一个智能指针类。智能指针是一种数据类型,一般用模板实现,模拟指针行为的同时还提供自动垃圾回收机制。它会自动记录SmartPointer对象的引用计数,一旦T类型对象的引用计数为零,就会释放该对象。

13.8 编写一个智能指针类。智能指针是一种数据类型,一般用模板实现,模拟指针行为的同时还提供自动垃圾回收机制。它会自动记录SmartPointer<T*>对象的引用计数,一旦T类型对象的引用计数为零,就会释放该对象。

解法:

智能指针跟普通指针一样,但他借助自动化内存管理保证了安全性,避免了诸如悬挂指针、内存泄漏和分配失败等问题。

智能指针必须为给定对象的所有引用维护单一引用计数。主要实现构造函数、复制构造函数和赋值运算符,析构函数。

 

C++实现代码:

#include<iostream>
#include<cstdlib>
#include<new>
using namespace std;

template <typename T>
class SmartPointer
{
public:
    SmartPointer(T* ptr)
    {
        ref=ptr;
        ref_count=(unsigned*)malloc(sizeof(unsigned));
        *ref=1;
    }
    SmartPointer(SmartPointer<T> &sptr)
    {
        ref=sptr.ref;
        ref_count=sptr.ref_count;
        ++(*ref_count);
    }
    SmartPointer<T> &operator=(SmartPointer<T> &sptr)
    {
        if(this==&sptr) return *this;
        if(*ref_count>0)
        {
            remove();
        }
        ref=sptr.ref;
        ref_count=sptr.ref_count;
        ++(*ref_count);
        return *this;
    }
    ~SmartPointer()
    {
        remove();
    }

    T getValue()
    {
        return *ref;
    }
protected:
    void remove()
    {
        --(*ref_count);
        if(*ref_count==0)
        {
            delete ref;
            free(ref_count);
            ref=NULL;
            ref_count=NULL;
        }
    }
private:
    T* ref;
    unsigned *ref_count;
};

int main()
{
    int *p1=new int();
    *p1=1111;
    int *p2=new int();
    *p2=22222;
    SmartPointer<int> sp1(p1),sp2(p2);
    SmartPointer<int> spa=sp1;
    sp2=spa;
}

 

相关文章
careercup-C和C++ 13.7
13.7 写一个函数,其中一个参数是指向Node结构的指针,返回传入数据结构的一份完全拷贝。 Node结构包含两个指针,指向另外两个Node。 C++实现代码: typedef map NodeMap; Node* copy_recursive(Node *cur, NodeMap &no...
714 0
careercup-C和C++ 13.9
13.9 编写支持对齐分配的malloc和free函数,分配内存时,malloc函数返回的地址必须都能被2的n次方整除。 解法:   一般来说,使用malloc,我们控制不了分配的内存会在堆里哪个位置。
660 0
|
存储 C++
careercup-C和C++ 13.10
13.10 用C编写一个my2DALLoc函数,可分配二维数组。将malloc函数的调用次数降到最少,并确保可通过arr[i][j]访问该内存。 解法: 这道题目最简单的方法就是先开一个数组来存储指向每一行的指针, 然后再为每一行动态地分配空间。
727 0
careercup-C和C++
13.1 用C++写个方法,打印输出文件的最后K行。 解答: 一种方法是打开文件两次,第一次计算文件的行数N,第二次打开文件,跳过N-K行, 然后开始输出。如果文件很大,这种方法的时间开销会非常大。
938 0
|
存储 C++
careercup-C和C++ 13.2
13.2 浅析哈希表和STL map。对比哈希表和STL map。哈希表是怎么实现的?如果输入数据规模不大, 我们可以使用什么数据结构来代替哈希表。 解答 对比哈希表和STL map 在哈希表中,实值的存储位置由其键值对应的哈希函数值决定。
842 0
|
存储 C++ 编译器
careercup-C和C++ 13.3
13.3 C++中的虚函数是如何工作的? 解答 虚函数依赖虚函数表进行工作。如果一个类中,有函数被关键词virtual进行修饰, 那么一个虚函数表就会被构建起来保存这个类中虚函数的地址。同时, 编译器会为这个类添加一个隐藏指针指向虚函数表。
790 0
careercup-C和C++ 13.4
13.4 深拷贝和浅拷贝有什么区别,如何使用?   解答 浅拷贝并不复制数据,只复制指向数据的指针,因此是多个指针指向同一份数据。 深拷贝会复制原始数据,每个指针指向一份独立的数据。通过下面的代码, 可以清楚地看出它们的区别: struct Test{ char *ptr; ...
715 0
|
C++ 编译器 C语言
careercup-C和C++ 13.5
13.5 谈谈C语言关键字”volatile”的意义(或重要性)? 解答 关键字volatile的作用是指示编译器,即使代码不对变量做任何改动,该变量的值仍可能被外界修改。操作系统、硬件或其他线程都可能修改该变量。
729 0
careercup-C和C++ 13.6
13.6 基类的析构函数为何要声明为virtual? 解答: 用对象指针来调用一个函数,有以下两种情况: 如果是虚函数,会调用派生类中的版本。 如果是非虚函数,会调用指针所指类型的实现版本。 析构函数也会遵循以上两种情况,因为析构函数也是函数嘛,不要把它看得太特殊。
800 0
|
16天前
|
存储 编译器 C语言
【c++丨STL】string类的使用
本文介绍了C++中`string`类的基本概念及其主要接口。`string`类在C++标准库中扮演着重要角色,它提供了比C语言中字符串处理函数更丰富、安全和便捷的功能。文章详细讲解了`string`类的构造函数、赋值运算符、容量管理接口、元素访问及遍历方法、字符串修改操作、字符串运算接口、常量成员和非成员函数等内容。通过实例演示了如何使用这些接口进行字符串的创建、修改、查找和比较等操作,帮助读者更好地理解和掌握`string`类的应用。
26 2