`

Java方法返回多种类型

    博客分类:
  • java
阅读更多

我的文章都整理添加到了个人博客中,大家可以添加这个RSS以便获得即时的文章信息。

 

说明:

1.本文讲述3种方式 如有更好方式 欢迎讨论

2.本例前准备:下载jar包:

  1. http://sourceforge.net/ 下搜索下载json-lib、ezmorph
  2. http://commons.apache.org/  下搜索下载以下jar
    lang(注意 不要使用最新的3.1 用2.6)、collections、beanutils

3.三种方式简要说明

  1. Json方式(目前web开发常用的方式)
  2. 集合方式(最容易想到)
  3. 泛型元组(最简单最实用)

4.具体内容看注释 写的很清楚,如有疑问欢迎讨论

 

1.测试类

package com.cxyapi.generics;

import java.util.HashMap;
import java.util.Map;
import java.util.Map.Entry;

import net.sf.json.JSONObject;

/** Java方法返回多种类型
 * @author cxy @ www.cxyapi.com
 */
public class ReturnMultipleResult
{
	public static void main(String[] args)
	{
		//方式一:使用json
		JSONObject result1=ReturnMultipleResult.way1();
		System.out.println(result1);
		JSONObject jos=(JSONObject)result1.get("s");
		System.out.println(jos.get("name"));
		/* JSONObject中存放的都是Object类型(其实是JSONObject类型)
		 * 如果想使用原来的类型,还需要其他的转换方式(toBean方法)
		 * 但是toBean方法 对于 有自定义构造函数的class,还需要一个init方法或定义映射
		 * 好麻烦呀~
		 * 并且这种方式还需要导入各种jar包
		 * 但是这种方式并不是一无是处,在action/controller层面还是很好用的,不适合纯业务处理的bo层。
		 */
		System.out.println("========================");
		
		//方式二:集合
		Map<String,Object> result2=ReturnMultipleResult.way2();
		System.out.println(result2);
		for(Entry<String, Object> one: result2.entrySet())
		{
			if(one.getKey().equals("s"))
			{
				Student s=(Student)one.getValue();
				s.show();
			}else if(one.getKey().equals("t"))
			{
				Teacher t=(Teacher)one.getValue();
				t.show();
			}
		}
		/* 这种方式采用Object超级父类来擦出类型差异
		 * 但是这种方式处理起来比较复杂,你需要自己判断到底是哪种类型的,并做相应的类型转化
		 */
		System.out.println("========================");
		
		//方式三:使用泛型元组
		TwoTuple<Student, Teacher> result3=ReturnMultipleResult.way3();
		result3.first.show();
		result3.second.show();
		System.out.println(new TwoTuple<String,Integer>("cxy",1));
		//应该不用多说了吧~ 优势太明显了,不用判断,不用转型,不用导入jar包,随意更换类型
	}
	
	//方式一:使用json返回多个结果对象
	public static JSONObject way1()
	{
		Student s=new Student("小明","清华大学");
		Teacher t=new Teacher("cxyapi", "Java编程");
		JSONObject backObject=new JSONObject();
		backObject.put("s", s);
		backObject.put("t", t);
		return backObject;
	}
	
	//方式二:集合方式
	public static Map<String,Object> way2()
	{
		Student s=new Student("小明","清华大学");
		Teacher t=new Teacher("cxyapi", "Java编程");
		Map<String,Object> backObject=new HashMap<String, Object>();
		backObject.put("s", s);
		backObject.put("t", t);
		return backObject;
	}
	
	//方式二:泛型元组
	public static TwoTuple<Student, Teacher> way3()
	{
		Student s=new Student("小明","清华大学");
		Teacher t=new Teacher("cxyapi", "Java编程");
		return new TwoTuple<Student, Teacher>(s,t);
	}
}

 

    元组:

package com.cxyapi.generics;

/** 元组  可以让一个方法返回多个对象
 * @author cxy @ www.cxyapi.com
 */
public class TwoTuple<A,B>
{
	/* 定义成final 是为了保证其安全性,不能进行修改
	 * public final 比private+getter/setter更符合当前的需求
	 */
	public final A first; 
	public final B second;
	
	public TwoTuple(A a,B b)
	{
		first=a;
		second=b;
	}
	
	public static TwoTuple<String,Integer> tupleTest()
	{
		return new TwoTuple<String,Integer>("cxy",1);
	}
	
	public static void main(String[] args)
	{
		System.out.println(TwoTuple.tupleTest().first);
		System.out.println(TwoTuple.tupleTest().second);
	}
}

 

   涉及到的Student类和Teacher类

package com.cxyapi.generics;

/**
 * @author cxy @ www.cxyapi.com
 */
public class Teacher
{
	private String name; // 姓名

	private String course; // 课程

	public Teacher(String name, String course)
	{
		this.name = name;
		this.course = course;
	}
	
	public void show()
	{
		System.out.println("我叫:"+this.name+",是一名"+this.course+"教师");
	}

	public String getName()
	{
		return name;
	}

	public void setName(String name)
	{
		this.name = name;
	}

	public String getCourse()
	{
		return course;
	}

	public void setCourse(String course)
	{
		this.course = course;
	}
}

 

package com.cxyapi.generics;

/**
 * @author cxy @ www.cxyapi.com
 */
public class Student
{
	private String name;  //姓名
	
	private String school;  //就读学校

	public Student(String name, String school)
	{
		this.name = name;
		this.school=school;
	}
	
	public Student init()
	{
		return new Student("1", "2");
	}

	public String getName()
	{
		return name;
	}

	public void setName(String name)
	{
		this.name = name;
	}

	public String getSchool()
	{
		return school;
	}

	public void setSchool(String school)
	{
		this.school = school;
	}
	
	public void show()
	{
		System.out.println("我叫:"+this.name+",就读于"+this.school);
	}

}

 

 

声明:

1.原创文章,转载请标明并加本文连接。

2.文章反映个人愚见,如有异议欢迎讨论指正

3.更多的内容请看我的  个人博客(测试版)

8
11
分享到:
评论
34 楼 wawxy2009 2013-03-24  
领教了~多谢
33 楼 mwei 2013-03-22  
snkcxy 写道
javaseer 写道
那如果想返回345678个对象元组还有办法做吗?

呵呵 继承就可以了


在方法调用时,被调用的方法如果返回多个不同类型的对象时,使用元组是不错的选择,为此方法写好javadoc就更好了。 至于返回3,4,5,6,7,8..N个对象,这...这个方法本身就有问题了,一次返回这么多不同类型的对象不太合理,可以使用LZ所言继承,将Tuple2扩展到TupleN(无奈之举,还是重构方法)。我平时只用Tuple2,Tuple3就很少用了。 当然Scala里提供到了22个元素的元组:
public class Tuple22 <T1, T2, T3, T4, T5, T6, T7, T8, T9, T10, T11, T12, T13, T14, T15, T16, T17, T18, T19, T20, T21, T22>  implements ... {
    private final T1 _1;
    private final T2 _2;
    private final T3 _3;
    private final T4 _4;
    ...


//下面的形式就够罗嗦了,方法本身就不够合理
return new Tuple2<List<YourType>,Map<String,YourType2>>(..., ..)

吸其精华,好用即可,接受拍。
32 楼 snkcxy 2013-03-21  
rainsilence 写道

public class Test {

	private int age;

	public static void main(String[] args) throws NoSuchFieldException, SecurityException {
		System.out.println(Test.class.getDeclaredField("age").getType().isPrimitive());
	}
}


嗯 这种方式确实能获得field的类型,学习了
那再想请教一下,如何获得方法内的变量的类型(尤其是基本类型)
31 楼 snkcxy 2013-03-21  
rainsilence 写道
学习方法是挺好的,将范例代码记下来。记得我6年前也是这么做的。更新了6年,现在资料已经有1.5G了。范围涉及到java全体,javascript全体(包括css,最新的html5的最佳实践代码),opengl算法,javafx2。感觉你还是处于初级阶段。慢慢来吧

嗯 确实 是初级阶段 还望前辈多多指点~
javafx2 我也很关注 用他写了一个即时通讯的小demo javafx2做界面连消息服务器
感觉需要改进的还很多,希望java8能有更好的表现,我是很期待呢~
30 楼 snkcxy 2013-03-21  
rainsilence 写道
http://www.cxyapi.com/java/oo/final.html

这篇,关键字final可讲的多了去了

1.多线程方向
由于java语言的不是为了并发而创建的。所以会有很多多线程方面的问题。其中最常见的就是内部类引用外部对象问题

java的规避方法就是当内部类要引用外部局部变量时,必须将局部变量变成final

etc

2.设计模式方向

不变模式

3.架构方向
Constants类,Util类最好都写成final的。

晕 这些不是问题吧?(我以为您指的问题是错误了)
我说过每一个知识点 都可以扩展出很多很多东西 尤其是和oo有关的东西
我写的是java基础 或者更准确的说是java入门
这些经验 和 最佳实践的不可能枚举的清楚。。。
但是能看出来这位朋友经验丰富肯定是前辈级的,还望前辈多多指点~
29 楼 rainsilence 2013-03-21  
学习方法是挺好的,将范例代码记下来。记得我6年前也是这么做的。更新了6年,现在资料已经有1.5G了。范围涉及到java全体,javascript全体(包括css,最新的html5的最佳实践代码),opengl算法,javafx2。感觉你还是处于初级阶段。慢慢来吧
28 楼 rainsilence 2013-03-21  
http://www.cxyapi.com/java/oo/final.html

这篇,关键字final可讲的多了去了

1.多线程方向
由于java语言的不是为了并发而创建的。所以会有很多多线程方面的问题。其中最常见的就是内部类引用外部对象问题

java的规避方法就是当内部类要引用外部局部变量时,必须将局部变量变成final

etc

2.设计模式方向

不变模式

3.架构方向
Constants类,Util类最好都写成final的。
27 楼 rainsilence 2013-03-21  
snkcxy 写道
MrCrapBag 写道

反射得到某个class对象后,比如说classFoo,那么classFoo.getName()就能获取一个类的唯一标识了。

当然,在osgi动态加载的时候,还要和对应加载类的classloader一起才能唯一确定一个类

呵呵 他说的这个是我的另一篇文章http://snkcxy.iteye.com/admin/blogs/1827913
反射获得对象类型 这个我写的很清楚了
其实我们讨论的是如何获取变量的基本类型问题
1.很多朋友看成是 判断是不是基本类型,但是我的文章是讨论获取是什么 而不是是不是~
2.有些人认为我写的多态方式没有实用价值 这个我也解释了 在普通运行的时候确实没有实用价值,因为基本类型 不存在不确定性,但是在动态加载运行类的时候 这个就稍具意义了

public class Test {

	private int age;

	public static void main(String[] args) throws NoSuchFieldException, SecurityException {
		System.out.println(Test.class.getDeclaredField("age").getType().isPrimitive());
	}
}


你说的写framework的时候(即动态加载类),如果类中有一个变量定义为基本类型,通过以上方法就可以判断。如果是局部变量,int i在传入方法的时候会自动类型转换。另外,你的动态方法真是太无语了,全是冗余代码,直接用泛型就ok了。在商业项目中,你的这种做法是绝对不允许的。
26 楼 snkcxy 2013-03-21  
MrCrapBag 写道

反射得到某个class对象后,比如说classFoo,那么classFoo.getName()就能获取一个类的唯一标识了。

当然,在osgi动态加载的时候,还要和对应加载类的classloader一起才能唯一确定一个类

呵呵 他说的这个是我的另一篇文章http://snkcxy.iteye.com/admin/blogs/1827913
反射获得对象类型 这个我写的很清楚了
其实我们讨论的是如何获取变量的基本类型问题
1.很多朋友看成是 判断是不是基本类型,但是我的文章是讨论获取是什么 而不是是不是~
2.有些人认为我写的多态方式没有实用价值 这个我也解释了 在普通运行的时候确实没有实用价值,因为基本类型 不存在不确定性,但是在动态加载运行类的时候 这个就稍具意义了
25 楼 snkcxy 2013-03-21  
MrCrapBag 写道
snkcxy 写道
jjcang 写道
做个返回对象,或者数组就可以了。

嗯 其实元组的方式就是返回对象,只不过类型不是定死的
嗯 数组倒是一种方式 Object[]


java有元组的概念吗?楼主所谓的元组,其实就是对象嵌套对象的做法吧。

顺便说一下,Object[]数组这种方式很不好哦,因为你拿到返回值之后,会做向下造型,这个时候你就要知道原来的类型是什么了,那你还得缓存每个对象的类型,而且在转换的时候,也是不安全的。

对 这位朋友说的很对
java中没有明确的元组概念 这个就算是模拟吧
Object[]方式肯定不好,这里只是说可以这样做(响应一下那个位朋友的讨论),但是真实情况下肯定不会去用Object去做这些事情。方式繁琐且不安全
24 楼 snkcxy 2013-03-21  
我觉得咱们讨论归讨论,每个人有自己的应用领域 所以对知识点的认知也不太一样
我不可能说出一个知识点的方方面面的应用,大家一起讨论讨论技术挺好
但是没必要 说 什么闭门造车,水平低啥的,每个人都有每个人的道理,谁对谁错都不一定,因为加载 “大环境” 的情况下,一切皆有可能~
当然 如果真的是哪里错了 我肯定虚心接受~
23 楼 snkcxy 2013-03-21  
MrLee23 写道
snkcxy 写道
MrLee23 写道
楼主的元组,不就是java中的枚举吗???????

呵呵 这个和枚举的概念还差很多吧 有空 看看enum 吧

我觉得你对枚举了解太少了,枚举是什么?枚举就是一个class,如果是一个class为什么不能携带多个对象?哎。。。希望你好好的了解和运用一下枚举,不要闭门造车。。。

晕 没人说不能携带呀。。。
我咋就闭门造车了呢 呵呵~
我个人理解枚举 意在枚举,枚举毕竟是以常量为主吧?有什么情况下需要你去枚举变量吗?
元组是类型和变量同事在变化的
所以我很难理解 这两个联系起来 有什么意义
当然你非得说他能当枚举 那肯定的  我定义一个数据 他也能当枚举呀~
22 楼 MrLee23 2013-03-21  
snkcxy 写道
MrLee23 写道
楼主的元组,不就是java中的枚举吗???????

呵呵 这个和枚举的概念还差很多吧 有空 看看enum 吧

我觉得你对枚举了解太少了,枚举是什么?枚举就是一个class,如果是一个class为什么不能携带多个对象?哎。。。希望你好好的了解和运用一下枚举,不要闭门造车。。。
21 楼 MrCrapBag 2013-03-21  
snkcxy 写道
rainsilence 写道
snkcxy 写道
rainsilence 写道
CXY API这个思路不错。。可惜内容是和作者的水平挂钩的。

所以,里面很多文章都有问题。

比如最后一篇,类型判断。

反射是万能的。你说无法判断基本类型

其实Class.isPrimitive方法就可以判断是否是基本类型。

呵呵 本人能力是有限 请多赐教
不过我说的是判断是哪种基本类型,不是判断是否是基本类型 这个有对应方法么?还没细研究过反射的所有方法 请赐教
还有哪些文章有问题 请赐教~

int.class.isPrimitive()

实际上是 我想做的是一个变量i 我想判断他是什么类型的(包括基本类型),而不是您说的是不是基本类型。不要问这有没有意义 之前的讨论说过这个问题。
是什么  和 是不是 是两个概念~
您不用回答是不是 这个不是我文章的内容,请您赐教 如何判断它是什么?


反射得到某个class对象后,比如说classFoo,那么classFoo.getName()就能获取一个类的唯一标识了。

当然,在osgi动态加载的时候,还要和对应加载类的classloader一起才能唯一确定一个类
20 楼 MrCrapBag 2013-03-21  
snkcxy 写道
jjcang 写道
做个返回对象,或者数组就可以了。

嗯 其实元组的方式就是返回对象,只不过类型不是定死的
嗯 数组倒是一种方式 Object[]


java有元组的概念吗?楼主所谓的元组,其实就是对象嵌套对象的做法吧。

顺便说一下,Object[]数组这种方式很不好哦,因为你拿到返回值之后,会做向下造型,这个时候你就要知道原来的类型是什么了,那你还得缓存每个对象的类型,而且在转换的时候,也是不安全的。
19 楼 snkcxy 2013-03-21  
rainsilence 写道
snkcxy 写道
rainsilence 写道
CXY API这个思路不错。。可惜内容是和作者的水平挂钩的。

所以,里面很多文章都有问题。

比如最后一篇,类型判断。

反射是万能的。你说无法判断基本类型

其实Class.isPrimitive方法就可以判断是否是基本类型。

呵呵 本人能力是有限 请多赐教
不过我说的是判断是哪种基本类型,不是判断是否是基本类型 这个有对应方法么?还没细研究过反射的所有方法 请赐教
还有哪些文章有问题 请赐教~

int.class.isPrimitive()

实际上是 我想做的是一个变量i 我想判断他是什么类型的(包括基本类型),而不是您说的是不是基本类型。不要问这有没有意义 之前的讨论说过这个问题。
是什么  和 是不是 是两个概念~
您不用回答是不是 这个不是我文章的内容,请您赐教 如何判断它是什么?
18 楼 snkcxy 2013-03-21  
MrLee23 写道
楼主的元组,不就是java中的枚举吗???????

呵呵 这个和枚举的概念还差很多吧 有空 看看enum 吧
17 楼 snkcxy 2013-03-21  
rainsilence 写道
snkcxy 写道
rainsilence 写道
CXY API这个思路不错。。可惜内容是和作者的水平挂钩的。

所以,里面很多文章都有问题。

比如最后一篇,类型判断。

反射是万能的。你说无法判断基本类型

其实Class.isPrimitive方法就可以判断是否是基本类型。

呵呵 本人能力是有限 请多赐教
不过我说的是判断是哪种基本类型,不是判断是否是基本类型 这个有对应方法么?还没细研究过反射的所有方法 请赐教
还有哪些文章有问题 请赐教~

int.class.isPrimitive()

我晕 大哥 int i=0; 如何判断 i是int 了解么? int.class我的文章里提到过的。
还有 我的文章还哪里有问题您说清楚了呀
16 楼 MrLee23 2013-03-20  
楼主的元组,不就是java中的枚举吗???????
15 楼 rainsilence 2013-03-20  
snkcxy 写道
rainsilence 写道
CXY API这个思路不错。。可惜内容是和作者的水平挂钩的。

所以,里面很多文章都有问题。

比如最后一篇,类型判断。

反射是万能的。你说无法判断基本类型

其实Class.isPrimitive方法就可以判断是否是基本类型。

呵呵 本人能力是有限 请多赐教
不过我说的是判断是哪种基本类型,不是判断是否是基本类型 这个有对应方法么?还没细研究过反射的所有方法 请赐教
还有哪些文章有问题 请赐教~

int.class.isPrimitive()

相关推荐

    Java方法返回多种类型.docx

    这篇文档介绍了三种在Java中实现方法返回多种类型的方法,包括使用JSONObject、集合Map以及泛型元组。以下是对这些方法的详细说明: 1. 使用JSONObject: - 在第一种方法中,通过将多个对象序列化到一个JSONObject...

    JAVA利用泛型返回类型不同的对象方法

    在Java编程中,泛型是一种强大的工具,它允许我们在类、接口和方法中定义类型参数,从而实现对多种数据类型的通用处理。泛型的主要目的是提高代码的类型安全性和重用性,减少类型转换的需要,并在编译时捕获可能的...

    Dwr源码示例,包含调用java方法返回不同的类型

    在这个"Dwr源码示例"中,我们将深入探讨如何使用DWR调用Java方法,并处理各种类型的参数和返回值。 首先,DWR的核心功能是提供了一种安全、高效的AJAX(异步JavaScript和XML)框架。它通过创建一个JavaScript到Java...

    mysql时间类型对应的java类型1

    - 当从数据库查询结果中获取时间类型时,会返回相应的Java SQL类型对象,例如`ResultSet.getDate()`, `ResultSet.getTime()`, 或 `ResultSet.getTimestamp()`。 示例代码展示了如何进行转换: ```java import ...

    java 泛型方法使用示例

    泛型方法是泛型技术在类方法层面的应用,它允许我们定义一个可以处理多种数据类型的通用方法。下面我们将深入探讨Java泛型方法的概念、语法以及使用示例。 **一、泛型方法概念** 泛型方法是一种具有类型参数的方法...

    java中String类型和int类型比较及相互转换

    本文将深入探讨Java中String类型和int类型之间的比较方法以及相互转换的技术,这对于理解和优化代码逻辑、提升程序性能具有重要意义。 ### 一、String类型与int类型的基本概念 #### 1.1 String类型 String类型在...

    Java类型检查,类型推断以及限制.pdf

    此外,`void`类型的Lambda表达式在Java中也有其特殊之处,如`Consumer&lt;T&gt;`接口,它接受一个类型为T的对象并执行某种操作,但不返回任何值。例如,`Consumer&lt;String&gt; b = s -&gt; list.add(s);`将字符串添加到列表中。 ...

    java 构造方法的资源

    构造方法与类名相同,没有返回类型,也不需要在方法签名中声明void。了解和熟练使用构造方法是Java面向对象编程的基础,下面将详细阐述Java构造方法的相关知识点。 一、构造方法的作用 构造方法的主要任务是在创建...

    java的Date类型转换成MySQL的DateTime类型.docx

    1. **创建转换方法**:定义一个名为`DateToMySQLDateTimeString`的方法,该方法接受一个`java.util.Date`对象作为参数,并返回符合MySQL `DateTime`格式的字符串。 2. **解析日期和时间**:利用`Date`对象的`...

    Java常用包

    * getReturnType()方法:返回方法的返回类型 * invoke()方法:调用方法 九、Field类 Field类提供了多种实例方法,包括: * get()方法:返回字段的值 * getGenericType()方法:返回字段的泛型类型 * getName()方法...

    java对象转换String类型的三种方法共1页.pdf

    `String.valueOf()`方法可以接受多种数据类型作为参数,包括基本类型和引用类型。对于对象,它实际上会调用对象的`toString()`方法。如果参数为null,它会返回"null"字符串。例如: ```java MyObject obj = new ...

    java-数据类型转换、运算符、方法入门_java_

    在Java编程语言中,数据类型转换、运算符和方法是构建程序的基础元素。这篇入门级资料将引导初学者深入理解这些关键概念。 首先,我们来探讨数据类型转换。Java提供了两种类型转换:自动类型转换(隐式转换)和强制...

    java中string和int型的相互转换.doc

    Java 中的 String 和 int 类型的相互转换是一个基本的数据类型转换操作,我们可以使用多种方法来实现这种转换,例如使用 `Integer.parseInt()` 方法、`Integer.valueOf()` 方法、`String.valueOf()` 方法等。...

    Java方法句柄1

    总的来说,Java方法句柄提供了一种高效且类型安全的方式来处理方法调用,它与反射和`invokeDynamic`指令结合,为Java应用程序提供了强大的动态性,尤其在实现动态语言和高性能代码生成场景中显得尤为重要。

    java常用工具类和接口返回对象.zip

    本压缩包"java常用工具类和接口返回对象.zip"很可能包含了多种实用的工具方法和设计模式,如工厂模式、单例模式等,用于处理常见的任务,如字符串操作、日期时间处理、集合操作等。 1. **StringUtil**:这个工具类...

    java方法通用返回结果集封装操作

    在 Java 编程中,方法的返回结果可以是各种类型的,如基本数据类型、对象、集合等。为了方便地处理返回结果,Java 提供了多种封装方式,包括使用 HashMap、泛型对象等。 1. 使用 HashMap 封装返回结果 使用 ...

    java 访问各种类型数据库的方法

    ### Java访问各种类型数据库的方法 #### 一、前言 在现代软件开发中,数据库扮演着极其重要的角色,用于存储和管理数据。Java作为一种广泛使用的编程语言,提供了多种方式来访问不同类型的数据存储系统。本文旨在...

    java-数组与方法及面向对象基础

    多态使得代码更加灵活,可以处理多种类型的数据。 为了实现面向对象编程,我们还需要了解构造器、抽象方法、接口、访问控制、重载和重写等概念。 构造器用于初始化新创建的对象,比如`public MyClass(int value) {...

    深入java虚拟机.pdf

    方法信息包括方法的名称、方法的返回类型、方法的参数列表等。 六、Java 虚拟机的垃圾收集 Java 虚拟机的垃圾收集是指在 Java 虚拟机中自动地回收不再使用的对象,以释放内存空间。垃圾收集可以是周期性的,也可以...

    高阶Java-Java枚举类型 enum 应用详解

    在这里,`Color`是枚举类型,`RED`, `GREEN`, `BLUE`是枚举的实例,它们默认继承自`java.lang.Enum`类。 2. 访问枚举实例: 你可以通过枚举类型直接访问其实例,例如: ```java Color color = Color.RED; ``` 3. ...

Global site tag (gtag.js) - Google Analytics