Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >专栏 >设计模式-创建者模式总结

设计模式-创建者模式总结

作者头像
高广超
发布于 2018-12-12 03:15:40
发布于 2018-12-12 03:15:40
43700
代码可运行
举报
文章被收录于专栏:互联网技术栈互联网技术栈
运行总次数:0
代码可运行

创建者模式的特点及使用场景

《Effective Java》—— 创建与销毁对象 一章中有写道:当一个类中有大量的构造参数时,静态方法和构造器已经不能满足对象的实例化,那么我们将考虑构建器。

构建器模式:

  • 1、重叠构造器模式
  • 2、javaBeans模式(自己常用的一种)
  • 3、builder模式

说明:

  • 重叠构造器模式:这种模式下,提供第一个只有必要参数的构造器,第二个构造器有一个可选参数,第三个有两个可选参数,以此类推,最后一个构造器包含所有可选参数。
  • javaBeans模式:调用在各分无参构造器创建对象,然后调用setter方法来设置每个必要的参数,以及每个相关的可选参数。
  • builder模式:builder像个构造器一样,可以对其参数强加约束条件。build方法可以检验这些约束条件。将参数从builder拷贝到对象中之后,并在对象域而不是builder域中对它们进行检验,这一点很重要。如果违反了人格约束条件,build方法就应该抛出IllegalStateException。异常的详细信息应该显示出违反哪个约束条件。

从上不难看出:

  • 重叠构造器模式在参数很多的情况下,客户端代码会很难写,并且难以阅读。
  • javaBeans模式因为构造过程分到了几个调用中,在构造过程中javaBean可能处于不一致的状态,类无法仅仅通过校验构造参数的* 有效性来保证一致性。这样程序员需要付出额外的努力来确保它的线程安全
  • builder模式技能保证像重叠构造器模式那样的安全性,也能保证像javaBeans模式那么好的可读性。

builder模式十分灵活,可以利用单个builder构建多个对象。builder的参数可以在创建对象期间进行调整,也可以随着不同的对象而改变。

代码示例

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
class DefaultHttpClientFactory {
    private static PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager();
    private static RequestConfig defaultRequestConfig = RequestConfig.custom().build();

    private static int mgrMaxTotal = DEFAULT_MAX_TOTAL;  //全局最大连接数
    private static int mgrDefaultMaxPerRoute = DEFAULT_MAX_PER_ROUTE; //每个主机最大连接数
    private static int connReqTimeout = DEFAULT_CONN_REQ_TIMEOUT;   //从连接池获取连接超时时间
    private static int connTimout = DEFAULT_CONN_TIMEOUT;   //发起连接超时时间
    private static int connSocketTimeout = DEFAULT_CONN_SOCKET_TIMEOUT;    //连接套接字等待时间

    public static class Builder {
        private int mgrMaxTotal = DEFAULT_MAX_TOTAL;  //全局最大连接数
        private int mgrDefaultMaxPerRoute = DEFAULT_MAX_PER_ROUTE; //每个主机最大连接数
        private int connReqTimeout = DEFAULT_CONN_REQ_TIMEOUT;   //从连接池获取连接超时时间
        private int connTimout = DEFAULT_CONN_TIMEOUT;   //发起连接超时时间
        private int connSocketTimeout = DEFAULT_CONN_SOCKET_TIMEOUT;    //连接套接字等待时间

        Builder() {
        }

        public Builder maxTotal(int maxTotal) {
            this.mgrMaxTotal = maxTotal;
            return this;
        }

        public Builder maxPerRoute(int maxPerRoute) {
            this.mgrDefaultMaxPerRoute = maxPerRoute;
            return this;
        }

        public Builder connReqTimeout(int connReqTimeout) {
            this.connReqTimeout = connReqTimeout;
            return this;
        }

        public Builder connTimout(int connTimout) {
            this.connTimout = connTimout;
            return this;
        }

        public Builder connSocketTimeout(int connSocketTimeout) {
            this.connSocketTimeout = connSocketTimeout;
            return this;
        }

        public DefaultHttpClientFactory build() {
            return new DefaultHttpClientFactory(this);
        }
    }

    private DefaultHttpClientFactory(Builder builder) {
        mgrMaxTotal = builder.mgrMaxTotal;
        mgrDefaultMaxPerRoute = builder.mgrDefaultMaxPerRoute;
        connReqTimeout = builder.connReqTimeout;
        connTimout = builder.connTimout;
        connSocketTimeout = builder.connSocketTimeout;
    }

    public static DefaultHttpClientFactory.Builder custom() {
        return new DefaultHttpClientFactory.Builder();
    }

    public CloseableHttpClient getClient() {
        cm.setMaxTotal(mgrMaxTotal); // 设置最大连接数
        cm.setDefaultMaxPerRoute(mgrDefaultMaxPerRoute); // 设置每个路由最大连接数,每个独立的host为1个路由
        RequestConfig requestConfig = RequestConfig.copy(defaultRequestConfig)
                .setConnectionRequestTimeout(connReqTimeout)//从连接池获取连接超时时间
                .setConnectTimeout(connTimout)//发起连接超时时间
                .setSocketTimeout(connSocketTimeout)//连接套接字等待时间
                .setRedirectsEnabled(false)
                .build();

        HttpClientBuilder httpClientBuilder = HttpClientBuilder.create();
        httpClientBuilder.setConnectionManager(cm);
        httpClientBuilder.setDefaultRequestConfig(requestConfig);

        httpClientBuilder.setRetryHandler(new DefaultHttpRequestRetryHandler(0, false)); // 去掉默认的3次重试
        CloseableHttpClient httpClient = httpClientBuilder.build();
        return httpClient;
    }
}

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2017.04.09 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
爬虫springboot服务假死nginx报502BadGateway
常用的三个状态是:ESTABLISHED 表示正在通信,TIMEWAIT 表示主动关闭,CLOSEWAIT 表示被动关闭。关于closewait和timewait,tcp中的交互图:
山行AI
2019/07/22
4.9K0
爬虫springboot服务假死nginx报502BadGateway
Java发送Http请求(HttpClient)
HttpClient 是Apache HttpComponents 下的子项目,用来提供高效的、最新的、功能丰富的支持 HTTP 协议的客户端编程工具包,并且它支持 HTTP 协议最新的版本和建议。HTTP 协议可能是现在 Internet 上使用得最多、最重要的协议了,越来越多的 Java 应用程序需要直接通过 HTTP 协议来访问网络资源。虽然在 JDK 的 java net包中已经提供了访问 HTTP 协议的基本功能,但是对于大部分应用程序来说,JDK 库本身提供的功能还不够丰富和灵活。HttpClient 是Apache HttpComponents 下的子项目,用来提供高效的、最新的、功能丰富的支持 HTTP 协议的客户端编程工具包,并且它支持 HTTP 协议最新的版本和建议。
ha_lydms
2023/08/09
1K0
HttpClient使用总结
根据业务量级决定使用同步调用或异步调用:异步回调方式的并发性非常高,缺点是代码可读性一般,在开发中,我会首先选择同步实现,在遇到性能问题后再考虑优化为异步回调方式。在Spring项目中使用HttpClient时,可以借用FactoryBean的概念,编写自己的HttpClientFactoryBean,我在LeanJava中写了一个例子:link
阿杜
2018/08/06
1.2K0
基于线程池创建HttpClient的请求
public class HttpClientUtils { private final static Logger logger = LoggerFactory.getLogger(HttpClientUtils.class); private static CloseableHttpClient httpClient; private static PoolingHttpClientConnectionManager manager; // 连接池管理类 private
Dream城堡
2022/01/07
9350
Java使用httpclient提交HttpPost请求(form表单提交,File文件上传和传输Json数据)
HttpClient 是 Apache Jakarta Common 下的子项目,用来提供高效的、最新的、功能丰富的支持 HTTP 协议的客户端编程工具包,并且它支持 HTTP 协议最新的版本和建议。Java后台使用httpclient主要目的是为了模拟客户端的请求。
I Teach You 我教你
2023/07/18
3.2K0
HttpClient详细解释
Http协议的重要性相信不用我多说了,HttpClient相比传统JDK自带的URLConnection,增加了易用性和灵活性(具体区别,日后我们再讨论),它不仅是客户端发送Http请求变得容易,而且也方便了开发人员测试接口(基于Http协议的),即提高了开发的效率,也方便提高代码的健壮性。因此熟练掌握HttpClient是很重要的必修内容,掌握HttpClient后,相信对于Http协议的了解会更加深入。
全栈程序员站长
2022/11/16
1.5K0
网关使用 Apache HttpClient 连接池出现异常
两个主机建立网络连接是一个比较复杂的过程,涉及到多个数据包的交换。建立网络连接本身就很耗时间,而 Http 连接需要三次握手,开销就更大。但是可以直接使用已经建立好的 Http 连接,那么花费就比较小。耗时更短,从而提高访问的吞吐量。
BUG弄潮儿
2022/06/30
9720
ElasticSearch源码分析之RestClient连接池
从上面的代码示例可以看出RestClient的实例化是依赖于RestClientBuilder的build方法,也就是应用了builder模式。HttpHost实例的构造方法入参为ip和端口。
山行AI
2020/04/22
9.2K0
ElasticSearch源码分析之RestClient连接池
HttpClient 在vivo内销浏览器的高并发实践优化
HttpClient作为Java程序员最常用的Http工具,其对Http连接的管理能简化开发,并且提升连接重用效率;在正常情况下,HttpClient能帮助我们高效管理连接,但在一些并发高,报文体较大的情况下,如果再遇到网络波动,如何保证连接被高效利用,有哪些优化空间。
2020labs小助手
2022/08/15
4100
聊聊HttpComponentsHttpInvokerRequestExecutor
本文主要研究一下HttpComponentsHttpInvokerRequestExecutor
code4it
2023/10/06
1670
聊聊HttpComponentsHttpInvokerRequestExecutor
HttpClient4.X 升级 入门 + http连接池使用
http://blog.csdn.net/shootyou/archive/2011/05/12/6415248.aspx
全栈程序员站长
2022/09/15
6370
Spring Cloud组件那么多超时设置,如何理解和运用?
版权声明:本文为博主原创文章,未经博主允许不得转载。 https://louluan.blog.csdn.net/article/details/90724258
亦山
2019/06/01
3K0
聊聊HttpComponentsHttpInvokerRequestExecutor
本文主要研究一下HttpComponentsHttpInvokerRequestExecutor
code4it
2023/10/03
2320
Http 持久连接与 HttpClient 连接池
HTTP协议是无状态的协议,即每一次请求都是互相独立的。因此它的最初实现是,每一个http请求都会打开一个tcp socket连接,当交互完毕后会关闭这个连接。
用户1257393
2018/07/30
2.1K0
Http 持久连接与 HttpClient 连接池
Apache HttpClient框架常用组件介绍
HttpClient 是 Apache Jakarta Common 下的子项目,用来提供高效的、最新的、功能丰富的支持 HTTP 协议的客户端编程工具包,并且它支持 HTTP 协议最新的版本和建议。HttpClient 已经应用在很多的项目中,比如 Apache Jakarta 上很著名的另外两个开源项目 Cactus 和 HTMLUnit 都使用了 HttpClient。
jack.yang
2025/04/05
960
使用Apache HttpClient编写Java爬虫
想要一个使用Apache HttpClient库的爬虫程序。首先,我需要确定用户的需求是什么。他们可能想用Java写一个网络爬虫,用来抓取网页内容。Apache HttpClient是一个常用的HTTP客户端库,用来发送HTTP请求和处理响应。所以,我需要先考虑如何用这个库来构造一个基本的爬虫程序。
华科云商小徐
2025/04/02
890
HttpClient Timeout设置
本教程主要讨论Apache HttpClient 4框架的timeout设置。如果想学习HttpClient的其他方面,请参考HttpClient教程。
九州暮云
2019/08/21
7.5K0
【Java爬虫】005-HttpClient学习笔记(补充:网页内容获取相关)
使用HttpClient可设置三种超时时间:RequestTimeout(获取连接超时时间)、ConnectTimeout(建立连接超时时间)、SocketTimeout(获取数据超时时间)。配置这三种超时时间,需要用到HttpClient的RequestConfig类中的方法custom(),该方法返回值为实例化的内部类Builder(配置器),其功能是配置先关请求的字段,还可以设置代理(proxy)、Cookie规范(cookieSpec)、是否允许HTTP相关认证等;
訾博ZiBo
2025/01/06
900
【微服务~远程调用】RestTemplate基本操作快速入门
👀专栏介绍 【微服务~远程调用】 目前主要更新微服务,一起学习一起进步。 👀本期介绍 本期主要介绍RestTemplate基本操作快速入门 文章目录 RestTemplate 概述 搭建环境 基本操作 HttpClient高级 SpringBoot整合HttpClient 概述 配置 测试:get请求 RestTemplate整合HttpClient 案例:管理员登录 分析 数据库 RestTemplate 概述 RestTemplate是Spring提供的用于访问Rest服务的客户端,RestTe
陶然同学
2023/02/27
3940
【微服务~远程调用】RestTemplate基本操作快速入门
Redis 客户端 Jedis 的那点事
作为分布式缓存系统之一,Redis 应用场景较为广泛,落地于不同的行业领域以及业务场景,因此,在整个架构拓扑中起着重要的作用。
Luga Lee
2021/11/22
2K0
Redis 客户端 Jedis 的那点事
推荐阅读
相关推荐
爬虫springboot服务假死nginx报502BadGateway
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验