终结函数(finalizer)通常是不可预测的,常常也是很危险的,一般情况下不是必要的。使用终结函数会导致不稳定的行为、更差的性能,以及带来移植性问题。不要把终结函数当做C++中的析构函数(destructors)的对应物。
我自己总结了一下这一条的综合性结论是这样的:
1)在涉及使用资源,使用完毕后要释放资源的情形下,首先要用一个显示的方法(应该是私有的)来释放这些资源;
2)在主方法中通过 try-catch-finally 的结构结合起来,try中写正常操作的代码,catch中处理异常,如写Log等,finally中通过调用1)中的显示的资源释放方法来释放资源(使用finally是因为不论成功还是异常都要释放资源)
3)用终结函数作为“安全网”,防止程序员忘记了2)中的“调用1)中的显示的资源释放方法”。这样迟一点释放资源也总比忘记释放要好;
4)进而用“终结守卫者”来代替3)中的终结函数,这样的好处是,如果这个类被子类继承,而子类的终结函数又忘记调用它的父类的终结函数时,如果父类是用“终结守卫者”来代替“终结函数”的话,就不怕子类遗忘此事了,即使子类的终结函数没有调用,父类的“终结守卫着”也会被执行的。
public class Example{
public void doSomething(){
try{
// 打开资源并使用
......
} catch XXXException e {
......
} finally {
release();
}
}
protected void release(){
// 释放资源
.......
}
private final Object finalizerGuardian = new Object(){
protected void finalize() throws Throwable{
release();
}
};
}
这一段尤其是最后的“终结守卫者”可以作为“定式”日后使用。
【Effective Java 学习笔记】系列连载专题请见:
http://tonylian.iteye.com/categories/64208
分享到:
相关推荐
6. **反作弊应用**:在游戏开发中,全局钩子常被用于反作弊措施,检测和阻止第三方作弊软件的活动。 通过深入理解并熟练掌握全局钩子技术,开发者可以构建功能强大的系统监控工具,但也需要意识到其潜在的风险和副...
3. **构造FIRST集**:对于每个非终结符,收集所有可能从它开始的句子的第一个终结符集合。 4. **构造FOLLOW集**:为每个非终结符计算在解析过程中可能出现的下一个输入符号的集合。 5. **冲突检测**:检查是否存在两...
4. 条款15-19是关于继承和对象的章节,探讨了继承的正确使用方式、如何处理对象的初始化和终结以及虚函数的正确使用。 5. 条款20-33主要讨论了模板和STL,覆盖了模板编程的基本原则、模板中的类型萃取和特性萃取,...
"福山历史的终结"在这里可能是指一个项目或教程的名字,暗示了这个压缩包内容可能是一个关于使用C语言处理PDF的完整教程或最终成果。 PDF文档格式是由Adobe公司开发的,用于在不同操作系统和硬件之间无损地交换文档...
LL(1)分析器的工作流程是:从输入序列的第一个符号开始,根据当前符号和文法的FIRST集(即非终结符可能生成的第一个符号集合)进行预测,如果当前符号可以被多个非终结符的第一符号覆盖,那么我们需要查看下一个符号...
### 第六章 实例域 讨论实例域的初始化、可见性、并发访问等,以及如何设计线程安全的类。 ### 第七章 类的复用 涵盖类和接口的复用策略,如组合优于继承、接口优于抽象类等。 ### 第八章 并发 讨论Java并发工具和...
第6章 程序结构(2) 245 6.1 函数指针 245 6.1.1 声明函数指针 246 6.1.2 函数指针作为实参 249 6.1.3 函数指针的数组 250 6.2 初始化函数形参 250 6.3 异常 252 6.3.1 抛出异常 253 6.3.2 捕获异常 254 ...
Win32 提供了一系列的 API 函数来完成线程的创建、挂起、恢复、终结以及通信等工作。 1. CreateThread 函数 HANDLE CreateThread(LPSECURITY_ATTRIBUTES lpThreadAttributes, DWORD dwStackSize, LPTHREAD_...
- 如果没有指定,则默认使用第一条语法规则的左端非终结符作为开始符号。 4. **语义值类型定义**: - 通过联合体定义多种类型的语义值。 - 使用`%union`定义联合体,并指定每种类型的名字。 - 使用`%type`指定...
每个非终结符对应一个函数,当遇到该非终结符时,调用相应的函数进行解析。 3. **递归子程序法工作原理**:此方法的核心在于,每一个非终结符都对应一个函数,这个函数会尝试匹配文法规则,并通过递归调用来处理子...
- 对于文法中的任意非终结符A,First(A)集合是指所有以A开头的句型的第一个符号集合。 - 若A → ε,则ε也属于First(A)。 2. **First 集合的应用** - 在LL(1)解析表的构建中起关键作用。 - 可用于预测分析器的...
6. **测试与调试**:使用不同的输入字符串测试文法分析器,确保其正确性和效率。 通过这个实习项目,我们可以深入理解编译器如何处理输入源代码,并且掌握LL(1)文法分析的具体实现方法。同时,C++语言的使用也让...
Swift中可以使用Core Data来管理数据模型,或者使用第三方数据库服务如Firebase。 - **评论功能**:评论系统需要处理用户输入、存储评论内容以及展示评论列表。利用SwiftUI或UIKit可以构建评论界面,结合网络请求...
2. **计算First集和Follow集**:First集代表非终结符可能产生的第一个符号,Follow集则表示在某个非终结符后面可能出现的符号。这些集合对于确定分析表中的动作至关重要。 3. **添加closure(闭包)操作**:根据...
托管C++最初设计时,其目标之一是尽可能地与标准C++兼容,避免引入任何新的关键字或语法结构,这导致了使用双下划线前缀来表示托管特性。然而,在C++/CLI的设计过程中,为了更好地支持Common Language ...
为了确保基因头部的第一个符号不是终结符,本文提出了一种改进的基因结构。在传统的GEP基因结构中添加了一个“身”部,使得基因由头、身、尾三部分组成。其中头部完全由函数符号构成,而身部相当于原来的头部。这种...
3. **构造LL(1)分析表**:LL(1)分析表是实现LL(1)解析器的关键,它包含两部分:First集合(每个非终结符的第一个符号集合)和Follow集合(每个非终结符的后继符号集合)。通过计算这两个集合,你可以构建出一个分析...