static对象

本文详细探讨了C++中静态对象的两种类型:局部静态对象和非局部静态对象,并解释了它们的生命周期特点及初始化顺序的不确定性。文章还提供了解决非局部静态对象间相互依赖问题的方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

static对象:一旦被创建,就一直存在,直到程序退出。

根据静态对象的位置不同,可以分为两类:non-local static object与local static object

具体来说:

local static object:指函数中用static修饰符修饰的object

生命期起始时间:在函数第一次调用时构造初始化。

生命期终止时间:程序结束

non-local static object:包括全局objects,在名词空间范围的objects,类中用static修饰符修饰的objects

生命期起始时间:在main函数调用之前被构造初始化。

生命期终止时间:程序结束

注意:在同一个文件或不同编译单元(不同文件)中,如果存在多个non-local static object,它们都是在主函数调用之前被构造的,但是它们之间的构造顺序时不定的。即对编译器来说,静态成员对象之间的初始化顺序和析构顺序是一个未定义的行为。

因此,不能用某个non-local static object去初始化non-local static object,无论这两个non-local static object在不在同一个编译单元中。

下面给出一个处在两个编译单元(CPP文件)中的non-local static object相互引用的情况:

class FileSystem 
{
public: …
	std::size_t numDisks() const;
};

extern FileSystem tfs;

//另一编译单元

class Directory 
{
public:
	Directory(params);
};

Directory::Directory(params) 
{
	std::size_t disks = tfs.numDisks();//使用另一个编译单元的静态变量
}

Directory tempDir (params);
由于编译器没有定义non-local static object之间的构造顺序,所以有可能类tfs还没有被构造,所以程序可能会报错。

解决方法:用local static对象替换non-local static对象。

C++保证,函数内的local static 对象会在该函数被调用期间,首次遇上该对象定义式时被初始化。

class FileSystem {…};

FileSystem& tfs() 
{
	static FileSystem fs;
	return fs;
}

//另一编译单元
class Directory {…};

Directory::Directory (params) 
{
	std::size_t disks = tfs().numDisks();//执行函数tfs时,对象fs肯定会被构造。
};

Directory& tempDir() 
{
	static Directory td;
	return td;
}

在 Java 中,可以使用 Mockito 框架来 mock `private static` 对象。下面是一个示例: 我们有一个类 `MyClass`,其中有一个 `private static` 对象 `myObject`: ```java public class MyClass { private static MyObject myObject = new MyObject(); public static void doSomething() { myObject.doSomethingElse(); } } ``` 现在我们想要 mock `myObject` 对象以便测试 `doSomething` 方法。我们可以使用 Mockito 的 `PowerMockito` 扩展来处理 `static` 方法和字段。 首先,我们需要在测试类中添加以下注解: ```java @RunWith(PowerMockRunner.class) @PrepareForTest(MyClass.class) ``` 然后,我们可以使用 `PowerMockito` 的 `mockStatic` 方法来 mock `myObject` 对象: ```java @Test public void testDoSomething() { MyObject mockedObject = Mockito.mock(MyObject.class); PowerMockito.mockStatic(MyClass.class); PowerMockito.when(MyClass.getMyObject()).thenReturn(mockedObject); MyClass.doSomething(); Mockito.verify(mockedObject).doSomethingElse(); } ``` 在这个测试中,我们首先创建一个 mock 对象 `mockedObject`,然后使用 `PowerMockito.mockStatic` 方法来 mock `MyClass` 类。接下来,我们使用 `PowerMockito.when` 方法来模拟 `MyClass.getMyObject` 方法并返回我们的 mock 对象。最后,我们调用 `MyClass.doSomething` 方法并验证 `mockedObject` 的 `doSomethingElse` 方法是否被调用。 需要注意的是,使用 `PowerMockito` 进行测试时,有些场景下可能需要添加一些额外的 Maven 依赖,例如 `powermock-module-junit4` 和 `powermock-api-mockito2`。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值