Java静态方法可能会产生代码异味

代码气味的定义 (来自维基百科):

“程序源代码中任何可能表明存在更深层问题的症状。”

在Java中, 静态方法允许您在“类范围”内执行代码,而不是像成员方法这样的实例范围。 这意味着,它们依赖于类级别的变量(如果有),传递给静态方法的参数或任何其他全局可访问的数据。 它们不是面向对象的。 对象具有与之关联的状态,并且只能通过实现该对象“行为”的方法进行操作。 静态方法不在状态上操作,它们不是面向对象的,实际上它们是过程式的。

这不好吗?

不会。尽管Java是面向对象的,但有时还是需要和/或首选Java中的类似于过程的编程。 任何面向对象的语言的真正威力在于能够在代码中紧密实现现实生活中的系统模型的能力(请参阅我有关面向对象建模的文章 )。 但是,即使在最核心的对象模型中,也很可能会有一些粘合代码或将以过程样式实现的基础结构代码。

因此,如果Java中的类似于过程的编程不是“那么糟糕”并且静态方法是过程编程的一种形式,那么静态方法是否不好?

嗯……答案并不像是“是”或“否”那么简单,无论您在其他博客上会读到什么,但我可能会不断争论着为什么这实际上是必须在上下文中做出的决定,因此,让我们重点关注一下我在Michael Minella博客的“如何模拟静态方法”中遇到的一组语句:

“已经成为该语言基础知识的部分(您要做的只是看一下Apache Commons项目以了解这一点)非常糟糕,以测试为名必须不惜一切代价避免。 Gosling(或其团队中的某人)出于某种原因将其放入语言中,并且仅由于您的工具集不支持对它的测试是无稽之谈而避免使用这些语言。 是时候获得新的工具集了。”

首先,我想指出的是,仅仅因为某种东西已经成为一种语言的基本组成部分,并不意味着它就是“好”或应该做的事情。 查看已检查的异常以供参考。 我记得EJB 1.x和2.x在过去成为Java EE的“基础”部分,因此也请参考一下。

其次,尽管我在理论上确实同意Michael的观点,即由于您的工具不支持某种特定的语言功能而使其愚蠢,但他的前提是静态方法。 避免使用静态方法是因为您的工具不支持静态方法,这根本不是胡说。 实际上,由一些好的测试和/或模拟框架( Mockito是我最喜欢的框架)引起的阻抗类型 :) )和静态方法可以确定地识别为代码异味。 这并不意味着我们不应该这样做,而是应该付出更多的努力来理解我们为什么这样做,并在存在“更深层次的问题”时探索替代方法。

我想指出,至少有两种类型的静态方法通常不会在测试/模拟框架中表现出太大的阻力。 第一种类型是用作实用程序方法的静态方法,就像在许多apache commons库或您自己的内部commons库中找到的方法一样。 这些通常是支持特定方法目标的例程,并且将它们模拟/存根到单元测试之外是没有意义的。 它们是实现的一部分,因此应进行测试。 第二种类型是静态方法,用于代替构造函数,如Joshua Bloch在他的书《 Effective Java》中所展示的。 静态方法的这种使用使您可以使用名称具有非常描述性的方法来构造新对象,以及其他一些优点。 第二种静态方法的分支可能包括工厂方法,但这取决于上下文。

当单元依靠静态方法执行超出该单元职责范围的逻辑时,由于静态方法和测试框架阻抗而产生的最明显的代码异味。 在这些情况下,您的测试框架将对您不利,因为您无法对范围外的逻辑进行存根/模拟,因为它是通过静态方法“硬编码”的。 这可以被视为“更深层的问题”,并且是大多数博客的焦点,这些博客告诉您不要使用静态方法,因为测试变得异常困难或不可能。 更改设计方法以遵循依赖性反转原则是另一种选择。 对如何测试单元的更好的理解是另一个。

我强烈断言,在使用静态方法的情况下,您可能会从测试框架中得到的回退表示代码有气味,而不是您需要尝试找到一个使用复杂的欺骗手段并将类加载器重新映射作为解决方案的框架。 应该准备评估一种特殊方法在其设计中的用途和基本缺陷。 Michael的博客文章使读者太容易采用新的工具/框架,仅因为Java支持静态方法并且您当前的测试框架阐明了一个阻抗-在这种情况下,阻抗反映了代码的味道,需要一些更深入,更批判性的思考。

参考: Java静态方法可能是 JCG合作伙伴 Christian Posta在Christian Posta Software博客上的代码味道 。


翻译自: https://www.javacodegeeks.com/2012/05/java-static-methods-can-be-code-smell.html

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

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

相关文章

android json 解析图片,JSON解析并获取android中的图像

我想解析包含字符串和图像的JSON对象。我的代码正在工作,但它加载图像太慢。我想加载另一个asynctask或服务的图像,以减少加载时间。我怎样才能做到这一点?哪一个是最好的方法使用asynctask或服务?这里是我的代码JSON解析并获取an…

Node Express4.x 片段视图 partials

1.在Express 4.x使用片段视图,需要引入partials模块 步骤: 1.在全局中安装express-partials模块: 2.在本地模块中安装express-partials,将模块安装到package.json中: 3.在入口文件(如:app.js)中引入模块: v…

bzoj1690:[Usaco2007 Dec]奶牛的旅行(分数规划+spfa判负环)

PS:此题数组名皆引用:戳我 题目大意:有n个点m条有向边的图,边上有花费,点上有收益,点可以多次经过,但是收益不叠加,边也可以多次经过,但是费用叠加。求一个环使得收益和/花费和最大&…

安全密码存储–请勿做的事和Java示例

安全存储密码的重要性 作为软件开发人员,我们最重要的职责之一就是保护用户的个人信息。 没有我们应用程序的技术知识,用户别无选择,只能相信我们正在履行这一责任。 令人遗憾的是,在密码方面,软件开发社区的记录不一。…

红米note4x Android7,红米Note4X能升级安卓7.0吗?红米Note4X如何升级Android7.0?

欢迎来到PPL网站的行业资讯知识分类,你现在观看的这篇文章要和大家分享的是关于红米Note4X能升级安卓7.0吗?红米Note4X如何升级Android7.0?的一些相关内容,希望大家能够感兴趣,并且希望我们能够帮助到你!在…

java基础----数字签名算法的介绍

数字签名(又称公钥数字签名)是一种类似写在纸上的普通的物理签名,但是使用了公钥加密领域的技术实现,用于鉴别数字信息的方法。关于数字签名的介绍,可以参见百度百科:http://baike.baidu.com/view/7626.htm…

Android宫格自动换行,九宫格视图的布局及展示(相册选择)

上周一个朋友带的项目出了点问题,招的ios开发人员在实现选取相册图片后用九宫格的样式展示时遇到了瓶颈,花了将近2周都没有解决。后来在跟我交流的过程中他把项目的图片发给我看了下,看完我就笑了,这就只是个算法的问题&#xff0…

具有LCS方法的通用文本比较工具

常见的问题是检测并显示两个文本(尤其是几百行或几千行)的差异。 使用纯java.lang.String类方法可能是一种解决方案,但是对于此类操作最重要的问题是,“性能”将不能令人满意。 我们需要一种有效的解决方案,其可能具有…

eclipse 开发 scala

(环境:jdk1.7,scala插件scala-2.1.1.2-site.zip) 1:下载scala插件 http://download.scala-ide.org/sdk/helium/e38/scala211/stable/site2:解压到本地将这两个文件里的jar包全部复制到eclipse的安装目录对应的文件夹里三:重启eclipse这时会提…

关于这个博客

博客主要打算写关于游戏制作方面的内容,包括directx,实时图形知识等等方面的内容,作为一个渣暂时都是一些简单的东西,努力找工作中...... 开这个博客主要目的是为了对自己做的事有个记录吧,并且关于directx方面的东西本…

Quartz Scheduler失火指令说明

有时,Quartz无法在您需要的时间运行您的工作。 这有三个原因: 所有工作线程都忙于运行其他作业(可能具有更高的优先级) 调度程序本身已关闭 该作业是在过去的开始时间安排的(可能是编码错误) 您可以通过…

android 代码获取屏幕图像,安卓获取屏幕以及获得像素点 ~ 大树洞

由于一些不可告人的需求,所以开始寻找各种可以实现安卓实时获得屏幕上某个像素点的功能首先,将需求进行拆解,分别为1、获得屏幕2、获得屏幕上一个像素点获得屏幕获得屏幕分为比较多种的方式,在以前大致分为adb screencap 获取当前…

海量端口扫描工具masscan

海量端口扫描工具masscanmasscan号称是互联网上最快的端口扫描工具,可以6分钟扫描整个互联网,每秒可以发送一百万个数据包。为了提高处理速度,masscan定制了TCP/IP栈,从而不影响本地其他TCP/IP的数据传输。masscan提供较为丰富的选…

改进租房练习

代码基本没有改动&#xff0c;函数有变化&#xff0c;老师只用了一个函数&#xff0c;自己做写了4个function&#xff0c;减少了代码量 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitio…

Google App Engine JAX-RS REST服务

在本文中&#xff0c;您将学习如何使用JAX-RS参考实现&#xff08;Jersey&#xff09;创建REST服务并将其部署在Google AppEngine上。 先决条件 对于本教程&#xff0c;您将需要&#xff1a; Google AppEngine帐户 Eclipse Galileo&#xff08;3.5.x&#xff09; 适用于Java的…

libnids校验和引起回放包不能正常捕捉

如题 取消校验和校验即可&#xff1a; struct nids_chksum_ctl temp;temp.netaddr 0;temp.mask 0;temp.action 1;nids_register_chksum_ctl(&temp,1); 在init之前。转载于:https://www.cnblogs.com/yaoyuanfeixing/p/6308067.html

鸿蒙系统的全面开源,华为:打造全球的操作系统,鸿蒙今日全面开源!

原标题&#xff1a;华为&#xff1a;打造全球的操作系统&#xff0c;鸿蒙今日全面开源&#xff01;今日下午&#xff0c;2019华为全球开发者大会在华为松山湖基地正式开幕。华为正式对外推出了自研操作系统——鸿蒙系统(Harmony OS)。华为消费者业务CEO余承东指出&#xff0c;鸿…

android 获取路径目录方法以及判断目录是否存在,创建目录

Environment 常用方法&#xff1a; * 方法&#xff1a;getDataDirectory()解释&#xff1a;返回 File &#xff0c;获取 Android 数据目录。* 方法&#xff1a;getDownloadCacheDirectory()解释&#xff1a;返回 File &#xff0c;获取 Android 下载/缓存内容目录。* 方法&…

Maven不会吮吸。 。 。 但是Maven文件会

我不会参加整个Maven辩论&#xff0c;但是可以说我是所有最佳实践的有力支持者&#xff0c;对我而言&#xff0c;Maven是最佳实践的体现。 我的意思是说&#xff0c;Maven是围绕特定的最佳实践构建方法构建的。 注意&#xff0c;我说了一种特定的最佳实践构建方法。 在现实世界…

html5 游戏制作教程,html5一步步实现超级玛丽游戏制作(新手教程源码)

【实例简介】【实例截图】【核心代码】My first Gamebody {border:none 0px;margin:0px;padding:10px;font-size : 16px;background-color : #f3f3f3;}canvas {border : 1px solid blue;}// 页面初始化函数function init(){//加载图片,并存入全局变量 ImgCache,// 加载完成后,调…