私有构造方法为什么要抛异常?

私有构造方法为什么要抛异常?

不知道有没有小伙伴浏览过JDK源码,发现有些私有构造方法里也要抛出异常。那么疑问来了?构造方法都私有了。也不能调用,抛异常不是多此一举吗?

答案是否定的。

先来看一个例子:java.util.Objects

public final class Objects {
    private Objects() {
        throw new AssertionError("No java.util.Objects instances for you!");
    }
}

在源码里抛出了一个异常,No java.util.Objects instances for you!,意思就是不能提供给你这个对象的实例。

之所以要抛异常是因为反射。
反射可以修改方法的访问权限,调用方法。

package reflect;

import org.junit.Test;

import java.lang.reflect.Constructor;
import java.util.Objects;

public class ClassPrivate {
    @Test
    public void test() {
        try {
            Class<?> clazz = Class.forName("java.util.Objects");
            Constructor<?> constructor = clazz.getDeclaredConstructor();// 获取构造方法
            constructor.setAccessible(true); // 修改private权限。true表示可以访问私有方法
            Objects objects = (Objects) constructor.newInstance();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

运行报如下错误。如果不在私有构造方法抛异常,那么该对象仍然能通过反射new出对象,这并非设计本意。现在应该懂了吧。如果确定类必须——不能被实例化。私有构造里也要抛异常哦~

原文地址:https://www.cnblogs.com/novae/p/12395044.html

时间: 2024-10-03 04:45:23

私有构造方法为什么要抛异常?的相关文章

Android(java)学习笔记108:通过反射获取私有构造方法并且使用

1 package cn.itcast_02; 2 3 import java.lang.reflect.Constructor; 4 5 /* 6 * 需求:通过反射获取私有构造方法并使用 7 * private Person(String name){} 8 * 9 * Person p = new Person("风清扬"); 10 * System.out.println(p); 11 */ 12 public class ReflectDemo3 { 13 public st

条款25:考虑写出一个不抛异常的swap函数

条款25:考虑写出一个不抛异常的swap函数 swap函数在C++中是一个非常重要的函数,但实现也非常复杂. 看一个缺省的std::swap函数的实现 namespace std { template<typename T> void swap( T& a , T& b) { T temp(a); a = b; b = temp } } ①内置类型的调用 int a = 2; int b =3; std::swap(a, b); cout<<"a:&quo

【PDF单页转化为图片输出 注意:英文或图片类的PDF可转化,中文抛异常】

1 public static void main(String[] args) throws IOException 2 { 3 /** 4 * PDF单页转化为图片输出 注意:英文或图片类的PDF可转化,中文抛异常 5 */ 6 PDDocument doc; 7 try 8 { 9 String inputFile = "F:\\java56班\\eclipse-SDK-4.2-win32\\iText入门基础教程[2].pdf"; 10 String imagepath = &

主动抛异常获取调试堆栈信息

android开发中常见的调试方法有: 下断点(break point)调试跟踪: 此方法局限性最大,要求程序是可中断,且非系统应用等. 打印日志(systemout.log都是此类): 此方法应用最广泛,也常在应用整个流程的关键位置或方法上记录,方便bug出现时的状态及流程获取.但是日志也仅局限于单个代码位置的状态记录,难以获取更广的上下文信息.本文要补充讨论的内容就是要解决这个问题: 通过获取命令调用的堆栈,来获取更全面的调试信息.至于如何获取这边提供主动抛异常的方法: try { thro

Effective C++ Item 25 考虑写出一个不抛异常的swap函数

本文为senlie原创,转载请保留此地址:http://blog.csdn.net/zhengsenlie 经验:当std::swap对你的类型效率不高时,提供一个swap成员函数,并确定这个函数不抛出异常 示例: stl里的swap算法 namespace std{ template<typename T> void swap(T &a, T &b){ T temp(a); a = b; b = temp; } } //"pimpl手法"(pointer

《Effective C++》item25:考虑写出一个不抛异常的swap函数

std::swap()是个很有用的函数,它可以用来交换两个变量的值,包括用户自定义的类型,只要类型支持copying操作,尤其是在STL中使用的很多,例如: int main(int argc, _TCHAR* argv[]) { int a[10] = {1,2,3,4,5,6,7,8,9,10}; vector<int> vec1(a, a + 4); vector<int> vec2(a + 5, a + 10); swap(vec1, vec2); for (int i =

Eclipse部署项目的时候抛异常【Multiple Contexts have a path of &quot;/cdcpm&quot;.】

Eclipse部署项目的时候抛异常[Multiple Contexts have a path of "/cdcpm".]重新clean .删除server都不好使.查看一下tomcat下的server.XML中多出一行context   删除掉也不好使.最后想起项目用Maven部署的,找到Eclipse下的server.XML 里面有两条同样path的Context, 删掉多出来的一行<Context docBase="cpms" path="/c

编写高质量代码改善C#程序的157个建议[用抛异常替代返回错误、不要在不恰当的场合下引发异常、重新引发异常时使用inner Exception]

原文:编写高质量代码改善C#程序的157个建议[用抛异常替代返回错误.不要在不恰当的场合下引发异常.重新引发异常时使用inner Exception] 前言 自从.NET出现后,关于CLR异常机制的讨论就几乎从未停止过.迄今为止,CLR异常机制让人关注最多的一点就是"效率"问题.其实,这里存在认识上的误区,因为正常控制流程下的代码运行并不会出现问题,只有引发异常时才会带来效率问题.基于这一点,很多开发者已经达成共识:不应将异常机制用于正常控制流中.达成的另一个共识是:CLR异常机制带来

AdapterView 不能设置 onClickListener,否则直接抛异常

@Override public void setOnClickListener(OnClickListener l) { throw new RuntimeException("Don't call setOnClickListener for an AdapterView. " + "You probably want setOnItemClickListener instead"); } AdapterView 不能设置 onClickListener,否则直