c++学习(特殊类设计)[30]

只能在堆上创建对象的类

如果你想要确保对象只能在堆上创建,可以通过将析构函数声明为私有,并提供一个静态成员函数来创建对象。这样,类的实例化只能通过调用静态成员函数来完成,而无法直接在栈上创建对象。

以下是一个示例:

class HeapOnlyClass {
private:HeapOnlyClass() {} // 私有的构造函数,防止在栈上创建对象~HeapOnlyClass() {} // 私有的析构函数public:static HeapOnlyClass* createInstance() {return new HeapOnlyClass();}
};int main() {// 无法在栈上创建对象// HeapOnlyClass obj;// 只能通过静态成员函数创建对象HeapOnlyClass* obj = HeapOnlyClass::createInstance();// 使用对象...delete obj; // 释放堆上的对象return 0;
}

在上面的示例中,HeapOnlyClass 类的构造函数和析构函数都被声明为私有。这意味着在类的外部无法直接创建对象或销毁对象。

通过提供一个静态成员函数 createInstance(),我们可以在堆上创建对象。静态成员函数返回一个指向 HeapOnlyClass 对象的指针。在 main() 函数中,我们使用 createInstance() 函数来创建对象,并在使用完对象后通过 delete 关键字释放对象。

这样,我们就可以确保对象只能在堆上创建,而无法在栈上创建。

只能在栈上创建对象的类

如果你想要确保对象只能在栈上创建,可以将类的构造函数声明为私有,并提供一个静态成员函数来创建对象。这样,类的实例化只能通过调用静态成员函数来完成,而无法直接在堆上创建对象。

以下是一个示例:

class StackOnlyClass {
private:StackOnlyClass() {} // 私有的构造函数,防止在堆上创建对象public:static StackOnlyClass createInstance() {return StackOnlyClass();}
};int main() {// 无法在堆上创建对象// StackOnlyClass* obj = new StackOnlyClass();// 只能通过静态成员函数创建对象StackOnlyClass obj = StackOnlyClass::createInstance();// 使用对象...return 0;
}

在上面的示例中,StackOnlyClass 类的构造函数被声明为私有。这意味着在类的外部无法直接创建对象。

通过提供一个静态成员函数 createInstance(),我们可以在栈上创建对象。静态成员函数返回一个 StackOnlyClass 对象。在 main() 函数中,我们使用 createInstance() 函数来创建对象,并在使用完对象后,对象会自动被销毁。

这样,我们就可以确保对象只能在栈上创建,而无法在堆上创建。

单例模式(一个类之只能创建一个对象)

在这里插入图片描述
在这里插入图片描述
单例模式可以通过懒汉模式和饿汉模式来实现。下面我将为你解释这两种方式的实现。

  1. 懒汉模式:
    懒汉模式是指在需要获取实例时才会创建对象。实现懒汉模式的关键是延迟实例化,即在第一次调用获取实例的方法时才创建对象。
class LazySingleton {
private:static LazySingleton* instance;LazySingleton() {} // 私有构造函数public:static LazySingleton* getInstance() {if (instance == nullptr) {instance = new LazySingleton();}return instance;}
};LazySingleton* LazySingleton::instance = nullptr;

在上面的示例中,LazySingleton 类的构造函数被声明为私有,无法直接实例化对象。通过静态成员变量 instance 来保存类的唯一实例,并在 getInstance() 方法中进行延迟实例化。如果 instancenullptr,则创建一个新的 LazySingleton 对象。如果 instance 不为 nullptr,则直接返回现有的实例。

  1. 饿汉模式:
    饿汉模式是指在类加载时就创建对象,无需延迟实例化。实现饿汉模式的关键是在类定义中直接创建对象,并提供一个静态方法来获取这个实例。
class EagerSingleton {
private:static EagerSingleton* instance;EagerSingleton() {} // 私有构造函数public:static EagerSingleton* getInstance() {return instance;}
};EagerSingleton* EagerSingleton::instance = new EagerSingleton();

在上面的示例中,EagerSingleton 类的构造函数被声明为私有,无法直接实例化对象。通过静态成员变量 instance 在类定义中直接创建 EagerSingleton 对象。在 getInstance() 方法中,直接返回这个已经创建好的实例。

懒汉模式和饿汉模式都可以实现单例模式,但它们的区别在于实例化的时机。懒汉模式在第一次调用获取实例的方法时才创建对象,而饿汉模式在类加载时就创建对象。

懒汉模式和饿汉模式各有优点和缺点,下面我将为你详细解释。

懒汉模式的优点:

  1. 延迟实例化:懒汉模式在需要获取实例时才会创建对象,可以避免不必要的资源消耗。如果实例化对象的过程比较耗时,懒汉模式可以提高性能。
  2. 线程安全(加锁):在多线程环境下,懒汉模式可以通过加锁来保证只有一个线程能够创建实例。这样可以避免多个线程同时创建多个实例的问题。

懒汉模式的缺点:

  1. 线程安全(加锁):虽然懒汉模式可以通过加锁来保证线程安全,但是加锁会引入额外的开销,降低性能。
  2. 可能存在资源竞争:在多线程环境下,如果有多个线程同时判断实例为空,然后同时创建实例,就会导致资源竞争的问题。

饿汉模式的优点:

  1. 简单直观:饿汉模式在类加载时就创建了实例,不需要进行延迟实例化的逻辑,代码相对简单。
  2. 线程安全:在类加载时就创建了实例,因此不会存在多个线程同时创建实例的问题。

饿汉模式的缺点:

  1. 提前实例化:饿汉模式在类加载时就创建了实例,如果这个实例在后续的程序中没有被使用,就会造成资源的浪费。
  2. 无法处理异常:在饿汉模式下,如果在创建实例的过程中发生异常,无法通过捕获异常来处理,因为实例的创建是在类加载时进行的。

综上所述,懒汉模式适用于需要延迟实例化的场景,可以避免不必要的资源消耗;而饿汉模式适用于实例创建比较简单且在后续程序中会被使用的场景,可以保证线程安全。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/55083.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

60多行代码仿制B站首页一个好看的卡片效果

文章目录 1、为啥是这个?2、仿制效果3、实现思路4、代码5、查看B站如何实现 1、为啥是这个? 看到Bilibili首页的一个卡片,看着效果很不错,给人很舒适的感觉。一琢磨貌似也不难,甚至只需要一层 div 就可以实现主要框架…

Microsoft Message Queuing Denial-of-Service Vulnerability

近期官方公布了一个MSMQ的拒绝服务漏洞,可能因为网络安全设备的更新,影响业务,值得大家关注。 漏洞具体描述参见如下: Name: Microsoft Message Queuing Denial-of-Service Vulnerability Description: Microsoft Message Queuing…

Kotlin~Mediator中介者模式

概念 创建一个中介来降低对象之间的耦合度,关系”多对多“变为“一对多”。 角色介绍 Mediator:抽象中介者,接口或者抽象类。ConcreteMediator:中介者具体实现,实现中介者接口,定义一个List管理Colleagu…

编译 intel MKL的一个fortran77 example DSYEV Example Program in Fortran

DSYEV Example Program in Fortran https://www.intel.com/content/www/us/en/docs/onemkl/code-samples-lapack/2023-1/dsyev-example-fortran.html 1. 示例代码 copy from hyperlink up: * Copyright (C) 2009-2015 Intel Corporation. All Rights Reserved. * The info…

并查集模板-两个操作:合并集合和查询两个元素是否属于同一个集合

一、链接 836. 合并集合 二、题目 一共有 nn 个数,编号是 1∼n1∼n,最开始每个数各自在一个集合中。 现在要进行 mm 个操作,操作共有两种: M a b,将编号为 aa 和 bb 的两个数所在的集合合并,如果两个数…

pip用法

pip show -f 包名 可以显示指定包的文件安装路径 参考: pip的基本使用 - 习久性成 - 博客园pip简介 1、pip 是一个现代的,通用的 Python 包管理工具。提供了对 Python 包的查找、下载、安装、卸载的功能。 2、pip是官方推荐的安装和管理Python包的工具…

2023华数杯数学建模竞赛选题建议

提示&#xff1a;DS C君认为的难度&#xff1a;C<B<A&#xff0c;开放度&#xff1a;B<A<C 。 A题&#xff1a;隔热材料的结构优化控制研究 A题是数模类赛事很常见的物理类赛题&#xff0c;需要学习不少相关知识。 其中第一问需要建立平纹织物整体热导率与单根纤…

【Linux操作系统】Vim:提升你的编辑效率

Vim是一款功能强大的文本编辑器&#xff0c;它具有高度可定制性和灵活性&#xff0c;可以帮助程序员和文本编辑者提高编辑效率。本文将介绍Vim的基本使用方法、常用功能和一些实用技巧。 文章目录 1. Vim的基本使用方法&#xff1a;2. 常用功能&#xff1a;2.1 文件操作&#…

物联网平台使用笔记

阿里云的IOT平台限制了50个设备。排除 移动云的限制较少&#xff0c;这里试用下。 创建完产品&#xff0c;接入设备后。使用MQTT客户端测试 其中client id 为设备id&#xff0c; username 为产品id&#xff0c; password 可以使用设备调试那里生成的。或使用官方token.exe 生成…

计算机网络(3) --- 网络套接字TCP

计算机网络&#xff08;2&#xff09; --- 网络套接字UDP_哈里沃克的博客-CSDN博客https://blog.csdn.net/m0_63488627/article/details/131977544?spm1001.2014.3001.5501 目录 1.TCP 1.服务端接口介绍 1.listen状态 2.accept获取链接 2.客户端接口介绍 2.TCP的服务器…

2023年 Java 面试八股文(20w字)

目录 第一章-Java基础篇 1、你是怎样理解OOP面向对象 难度系数&#xff1a;⭐ 2、重载与重写区别 难度系数&#xff1a;⭐ 3、接口与抽象类的区别 难度系数&#xff1a;⭐ 4、深拷贝与浅拷贝的理解 难度系数&#xff1a;⭐ 5、sleep和wait区别 难度系数&a…

TPlink DDNS 内网穿透?外网访问设置方法

有很多小伙伴都想知道&#xff1a;TPlink路由器怎么设置DDNS内网穿透&#xff1f;今天&#xff0c;小编就给大家分享一下TPlink DDNS 外网访问设置方法&#xff0c;下面是图文教程&#xff0c;帮助新手快速入门DDNS设置。 本文介绍的是云路由器TP-LINK DDNS的设置方法。TP-LIN…