`
hynuliuyi
  • 浏览: 1752 次
  • 性别: Icon_minigender_1
  • 来自: 广州
最近访客 更多访客>>
社区版块
存档分类
最新评论

项目中List的返回值

阅读更多
最近公司一个已经稳定运行了1年的web系统出现了性能问题,响应速度非常慢,系统是不断注册新的模块的,每次增加新模块都会带来一定负载,虽然很快就断定是由于大量模块的配置文件加载与初始数据缓存本身占用了大量内容,导致留给用户操作内存空间小造成,最好的办法就是卸载无用模块和清理缓存数据,但领导还是坚持要求检查代码并消除浪费内存的低效代码,系统比较大,这件事做起来可不容易,呵呵…
在检查的时候,发现方法中对无数据集合类型的返回有2种方式,Null和new List,系统是由很多人开发的,根据代码上看很明显没有对这些细节形成统一的规范,不过也能理解…
随便找人问了问,然后告诉他们以后规范方面尽量统一,至于上面的问题返回null还是创建一个空内容数组,由于系统刚出现内存问题,几乎统一了意见,用null吧…
真是这样吗?创建新对象返回时为了避免客户端代码的空值验证,返回null值是为了减少开销,视乎都有道理。其实个人觉得不应该返回空,当然,这里暂时不考虑业务需要的情况。但内存开销怎么办?无数据集合基本上是不变的,开销应该是很低的,不过还是有两全其美的办法,不知道大家对Collections工具类的empty系列静态方法用的多不多,这些方法返回一个无内容集合,并且都是基于同一个对象实例,这样,就可以避免null值的验证和那一点开销了,建议大家大量使用


举例:
public List returnArray2(Object data){
	if(data == null){
		return Collections.emptyList();
	}
	return (List) data;
}


当然还有Collections.emptyMap()、Collections.emptySet(),原理是一样的
另外,也可以选择Collections的静态变量进行返回,其实上述方法中返回的就是下面的Collections中定义的静态变量:
public static final List EMPTY_LIST = new EmptyList();
public static final Set EMPTY_SET = new EmptySet();
public static final Map EMPTY_MAP = new EmptyMap();

在jdk1.5之前的版本使用只能使用静态变量的方式访问,具体可以见jdk源码

分享到:
评论
30 楼 treblesoftware 2010-01-22  
anky_end 写道
fengsage 写道
谢谢LZ,学到了。原来返回null也会在占用一定空间啊·~~~看来影响程序性能的瓶颈还真多啊~~

我觉得楼主说的已经很明白
楼主并不认为new List会占用多少内存,出问题的是其他原因。

我还是坚持这个观点,即使直接返回个new List也不会有什么问题。这种短期对象很快就被回收了。

会出问题的是长期驻留在内存的东东,比如楼主说的配置模块缓存


哎,还有可能是过多的HTTPSESSION对象导致内存被过多占用,返回一个NULL,能占多少?而且这些对象几乎都是无状态的,很容易就被X掉。当然,虚拟机会在对象太多时进行垃圾回收,这时候也许性能会比较差,我认为LZ的问题是不是出在过多的有状态对象上,比如:HTTPSESSION。
29 楼 anky_end 2010-01-22  
fengsage 写道
谢谢LZ,学到了。原来返回null也会在占用一定空间啊·~~~看来影响程序性能的瓶颈还真多啊~~

我觉得楼主说的已经很明白
楼主并不认为new List会占用多少内存,出问题的是其他原因。

我还是坚持这个观点,即使直接返回个new List也不会有什么问题。这种短期对象很快就被回收了。

会出问题的是长期驻留在内存的东东,比如楼主说的配置模块缓存
28 楼 sunsong 2010-01-22  
anky_end 写道
sunsong 写道
凤舞凰扬 写道
nickevin 写道
Item 43: Return empty arrays or collections, not nulls

public List<Cheese> getCheeseList() {
  if (cheesesInStock.isEmpty())
    return Collections.emptyList(); // Always returns same list
  else
    return new ArrayList<Cheese>(cheesesInStock);
}


from Effective Java : Joshua Bloch

   包括楼主以及楼上在内的童鞋们请注意:
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。
   所以大家对于书的理解,对于程序的理解,切记要在一定范围内。

没试过,不知道说的填充异常,具体是如何产生的。

List list1 = Collections.emptyList();  
list1.add("a");

抛异常。。。。就这样。

ORM延迟加载会有这样的情况吗?如果主实体是一个emptyList,怎么会加载子实体呢?
27 楼 fengsage 2010-01-21  
谢谢LZ,学到了。原来返回null也会在占用一定空间啊·~~~看来影响程序性能的瓶颈还真多啊~~
26 楼 anky_end 2010-01-21  
sunsong 写道
凤舞凰扬 写道
nickevin 写道
Item 43: Return empty arrays or collections, not nulls

public List<Cheese> getCheeseList() {
  if (cheesesInStock.isEmpty())
    return Collections.emptyList(); // Always returns same list
  else
    return new ArrayList<Cheese>(cheesesInStock);
}


from Effective Java : Joshua Bloch

   包括楼主以及楼上在内的童鞋们请注意:
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。
   所以大家对于书的理解,对于程序的理解,切记要在一定范围内。

没试过,不知道说的填充异常,具体是如何产生的。

List list1 = Collections.emptyList();  
list1.add("a");

抛异常。。。。就这样。
25 楼 sunsong 2010-01-21  
凤舞凰扬 写道
nickevin 写道
Item 43: Return empty arrays or collections, not nulls

public List<Cheese> getCheeseList() {
  if (cheesesInStock.isEmpty())
    return Collections.emptyList(); // Always returns same list
  else
    return new ArrayList<Cheese>(cheesesInStock);
}


from Effective Java : Joshua Bloch

   包括楼主以及楼上在内的童鞋们请注意:
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。
   所以大家对于书的理解,对于程序的理解,切记要在一定范围内。

没试过,不知道说的填充异常,具体是如何产生的。
24 楼 anky_end 2010-01-20  
另外就是new对象,我个人看法,直接new个list返回回去,也耗费不了什么资源,当然没有empty实现好
23 楼 anky_end 2010-01-20  
hkliya 写道
凤舞凰扬 写道
引用
empty实现只占用一份内存,而且基本对象的内存占用我认为是很低的,而且如果没意外很快也就回收了。

   这句真没看懂....

可能他的意思是说:
        List list1 = Collections.emptyList();
        List list2 = Collections.emptyList();
        System.out.println(list1 == list2);//true

不好意思,很久没关注了,
谢谢哥哥替我解释。

22 楼 treblesoftware 2010-01-19  
内存紧缩的问题是不是出在过多人的登录上?过多的HTTPSESSION似乎很占用服务器内存。
21 楼 風一樣的男子 2010-01-18  
凤舞凰扬 写道
nickevin 写道
Item 43: Return empty arrays or collections, not nulls

public List<Cheese> getCheeseList() {
  if (cheesesInStock.isEmpty())
    return Collections.emptyList(); // Always returns same list
  else
    return new ArrayList<Cheese>(cheesesInStock);
}


from Effective Java : Joshua Bloch

   包括楼主以及楼上在内的童鞋们请注意:
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。
   所以大家对于书的理解,对于程序的理解,切记要在一定范围内。


学习了,在以后的开发中会注意,javaeye 里大牛不少
20 楼 hkliya 2010-01-18  
凤舞凰扬 写道
引用
empty实现只占用一份内存,而且基本对象的内存占用我认为是很低的,而且如果没意外很快也就回收了。

   这句真没看懂....

可能他的意思是说:
        List list1 = Collections.emptyList();
        List list2 = Collections.emptyList();
        System.out.println(list1 == list2);//true
19 楼 凤舞凰扬 2010-01-18  
   我们要把问题分成两个部分:
1. 对于一个类来说,它的方法返回的集合类型是否可写。
2. 对于返回空集合的情况,方法究竟改返回什么Null, EmptyXXX 或者new XXX(0).

   对于前者,其实不是讨论的重点,它一般是出现在服务类,并且应该是由服务行为(也就是方法行为)所描述或者确定的。
   对于后者,如果已经确认方法应该返回不可写的集合(比如服务类),那么应该返回EmptyXXX,这样一是保证不可写,而是避免客户程序空指针异常。(一个好的业务程序不应该让客户程序有不一致的理解) 而如果是实体类,比如用来进行关系映射的对象,就应该使用new XXX() ,比如new ArrayList()的方式(当然大小可自己限制确定)。 楼上有位童鞋说的
引用
难怪JPA返回的resultList是不可写的,也无法装载了。
其实是指EntityManager(服务类)执行query返回的结果集,而不是对象映射中的子对象集合(子对象集合如果是非可写的,并且子对象被映射成可写映射,就会出异常的)。
18 楼 BarryWei 2010-01-18  
凤舞凰扬 写道
引用
empty实现只占用一份内存,而且基本对象的内存占用我认为是很低的,而且如果没意外很快也就回收了。

   这句真没看懂....

这个意思大概应该是:返回的那个empty list是一个static的list,在内存中只有一个。
17 楼 凤舞凰扬 2010-01-18  
引用
empty实现只占用一份内存,而且基本对象的内存占用我认为是很低的,而且如果没意外很快也就回收了。

   这句真没看懂....
16 楼 sunjun 2010-01-18  
return new ArrayList(0); 这样就行吧
15 楼 anky_end 2010-01-18  
BarryWei 写道
引用
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。


ORM的时候返回不可写的集合,也是问题的根源之一吧。至少这个空的集合还是被分配了内存出来。

如果规范统一起来,都返回null,可能会好点吧?

empty实现只占用一份内存,而且基本对象的内存占用我认为是很低的,而且如果没意外很快也就回收了。

14 楼 BarryWei 2010-01-17  
引用
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。


ORM的时候返回不可写的集合,也是问题的根源之一吧。至少这个空的集合还是被分配了内存出来。

如果规范统一起来,都返回null,可能会好点吧?
13 楼 C_J 2010-01-17  
凤舞凰扬 写道
nickevin 写道
Item 43: Return empty arrays or collections, not nulls

public List<Cheese> getCheeseList() {
  if (cheesesInStock.isEmpty())
    return Collections.emptyList(); // Always returns same list
  else
    return new ArrayList<Cheese>(cheesesInStock);
}


from Effective Java : Joshua Bloch

   包括楼主以及楼上在内的童鞋们请注意:
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。
   所以大家对于书的理解,对于程序的理解,切记要在一定范围内。


难怪JPA返回的resultList是不可写的,也无法装载了。

看来楼主要注意了,我想你把所有返回都改写可能会带来风险!!
12 楼 hynuliuyi 2010-01-16  
凤舞凰扬 写道
nickevin 写道
Item 43: Return empty arrays or collections, not nulls

public List<Cheese> getCheeseList() {
  if (cheesesInStock.isEmpty())
    return Collections.emptyList(); // Always returns same list
  else
    return new ArrayList<Cheese>(cheesesInStock);
}


from Effective Java : Joshua Bloch

   包括楼主以及楼上在内的童鞋们请注意:
1. 对于服务层或者提供服务的类(比如工具类)等,使用默认的empty实现(不仅仅是List,还包括Set, Map等数据结构类)是正确的选择。这样可以避免客户程序调用时对返回值的理解不一致从而出现的NullPointerException。
2. 对于数据实体类,用于ORM映射时(比如domain层),就要小心了,不要随便返回empty实现。尤其是使用了LazyLoading技术来进行一对多mapping时。因为默认的empty实现都是不可写的。这个时候,如果ORM试图延迟装载对应的实体类时(访问主实体时,子实体集合是空的;而第一次访问子实体集合时,ORM会去装载子实体,并填充集合),就会出现异常。
   所以大家对于书的理解,对于程序的理解,切记要在一定范围内。



非常赞同,开发过程中应该在遵循规范的同时,考虑实际情况作出灵活的变改,规范是死的,程序是活的
11 楼 shadowlin 2010-01-16  
0dragon 写道
return null 有造成null pointer exception的可能吧...
所以取之前要判断是否为null

但是逻辑上也还是要判断集合是不是空的啊。

相关推荐

    C++2005调用C#Webservice接口返回值为List

    C++2005调用C#Webservice接口返回值为List 本文将详细介绍C++2005如何调用C#Webservice接口返回值为List。首先,需要了解C#Webservice的基本概念和C++2005如何调用Webservice接口。 一、C#Webservice的基本概念 ...

    ASP.NET—001:GridView绑定List、页面返回值

    "ASP.NET—001:GridView绑定List、页面返回值"的主题涉及了如何将数据源绑定到GridView以及处理页面间的数据传递。 首先,让我们深入理解GridView的绑定机制。在ASP.NET中,GridView可以绑定到各种数据源,包括但...

    Java List集合返回值去掉中括号(&#39;[ ]&#39;)的操作

    使用如下方式调用`strip()`方法去除List集合返回值中的中括号: ```java String listString = "[element1, element2, element3]"; String strippedString = StringUtils.strip(listString, "[]"); ``` 在完成上述...

    WebApi接口返回值不困惑:返回值类型详解 - 文章 - 伯乐在线1

    // 实际项目中填充lstRes return Json(lstRes); } ``` 这个接口将返回一个包含多个`ORDER`对象的JSON数组给客户端。 - **Ok(T content)**:返回HTTP状态码200(OK)和指定的内容。 - **BadRequest()**: 返回...

    IntelliJ IDEA自动设置代码注释的方法(带参数,带返回值,如果没有则跳过参数或返回值方法

    在日常的软件开发过程中,良好的代码注释习惯对于项目的维护和团队协作至关重要。对于习惯了Visual Studio(简称VS)开发环境中的.NET开发者来说,按下`///+Tab`键即可自动生成带有参数和返回值的代码注释,这大大...

    在服务器端得到CheckBoxList控件最后选择项的方法

    ### 在服务器端获取CheckBoxList控件最后选择项的方法 #### 一、背景介绍 在Web开发中,`CheckBoxList`控件是一种...在实际项目中,可以根据具体需求对以上代码进行适当的调整和优化,以更好地满足业务逻辑的需求。

    ASP.NET―001:GridView绑定List、页面返回值具体实现

    用惯了WPF的绑定,ASP.NET的绑定貌似不是很好用。下面看看ASP.NET绑定的用法。一般来说可以直接绑定DataTable的,不过我觉得绑定List比较...项目结构: 效果: 实体类 代码如下:public class PersonModel { private i

    java传list给存储过程,项目提取,不忽悠

    在Java开发中,有时我们需要将数据集合,如List,传递给数据库中的存储过程进行处理。这个过程涉及到Java的JDBC(Java Database Connectivity)操作、集合处理以及与数据库交互的细节。下面将详细讲解如何在Java中...

    springboot整合mybatis,接口返回值利用pagehelper实现分页

    在本文中,我们将深入探讨如何在SpringBoot项目中整合MyBatis,并利用PageHelper插件实现接口返回值的分页功能。SpringBoot以其简洁、快速的特性,成为了现代Java开发中的首选框架,而MyBatis作为轻量级的持久层框架...

    java传list给存储过程,项目提取,不忽悠源码整理

    在Java编程中,将List对象传递给存储过程是一项常见的任务,特别是在进行数据库操作时。存储过程是数据库中预编译的SQL语句集合,可以接受参数、返回结果集以及执行复杂的业务逻辑。以下是对这个主题的详细阐述: 1...

    webservice cxf spring整合返回list,bean,string,json,xml项目完整实例

    【标题】:在Java EE环境中,使用Apache CXF与Spring框架整合实现Web服务,返回List、Bean、String、JSON及XML的完整项目实例 【描述】:本项目旨在展示如何在Java企业级应用(Java EE)中,通过Apache CXF框架创建...

    dwr调用带集合返回值的方法

    1. **配置DWR**: 首先,你需要在项目中配置DWR。这通常包括创建`dwr.xml`配置文件,定义允许客户端调用的服务器端类和方法。例如,你可以指定一个包含集合返回值的方法: ```xml ``` 这里`MyClass`是...

    dwr各种例子(各种数据类型返回值+包+导入可用+注释+附带讲解)

    在这个压缩包中,你将找到一系列DWR的例子,涵盖了多种数据类型的返回值,这些例子旨在帮助初学者更好地理解和使用DWR。 1. **基本数据类型**: DWR支持Java的基本数据类型,如int、double、String等。通过DWR,你...

    商业编程-源码-在List Control中实现列表项目的上下移动.zip

    本资源“商业编程-源码-在List Control中实现列表项目的上下移动.zip”提供了一种方法,允许用户在列表控件中上下移动列表项,这对于创建具有动态排序功能的应用程序非常有用。本文将深入探讨如何实现这一功能,并...

    精彩编程与编程技巧-快速选择里List全部项目...

    根据给定的信息,本文将详细解释如何在编程中快速选择列表(List)中的所有项目,并深入探讨其中涉及到的关键概念和技术。 ### 一、快速选择列表(List)中的所有项目 #### 1.1 概述 在许多应用程序中,列表(List)是...

    listCtrl控件

    在C++编程中,MFC(Microsoft Foundation Classes)是一个用于构建Windows应用程序的类库,它提供了许多方便的类,使得开发者能够更容易地处理...通过ListDemo项目中的示例,开发者可以更直观地了解并实践这些知识点。

    VC++ ListCtrl设置颜色

    在实际应用中,`ColoredListCtrl`这个文件可能是实现颜色设置功能的一个类或一个示例项目。它可能扩展了CListCtrl,提供了更加方便的方法来设置不同项或子项的颜色,比如根据条件改变颜色,或者支持高亮、选中状态下...

    mfc下的listctrl控件使用

    在提供的`ListCtrlDemo` 文件中,可能包含一个示例项目,演示了如何创建、填充并排序`CListCtrl` 控件。`www.pudn.com.txt` 可能包含了项目的相关说明或源代码。 ### 结论 `CListCtrl` 在MFC编程中扮演着重要角色,...

    list_lru.rar_Always

    标题中的"list_lru.rar_Always"提示我们关注的是一个与LRU(Least Recently Used,最近最少使用)算法相关的代码库或项目。LRU是一种常用的缓存淘汰策略,当缓存满时,它会优先淘汰最久未使用的数据。在这个上下文中...

Global site tag (gtag.js) - Google Analytics