>  기사  >  Java  >  자바 제네릭 학습 예제

자바 제네릭 학습 예제

高洛峰
高洛峰원래의
2017-01-18 11:08:441185검색

Java Generics(Generics)는 JDK5에 도입된 새로운 기능으로, 클래스와 인터페이스를 정의할 때 유형 매개변수(Type Parameter)를 사용할 수 있도록 해줍니다. 선언된 유형 매개변수는 사용 시 특정 유형으로 대체됩니다. 이제 제네릭의 가장 중요한 애플리케이션은 Map 및 List가 사용되는 JDK5의 새로운 컬렉션 클래스 프레임워크입니다. 장점은 자명합니다. 더 많은 클래스를 수평으로 확장할 수 있지만 단점은 실제로 장점입니다. 왜냐하면 일반 클래스를 사용할 때 코드의 목적을 매우 명확하게 해야 하고 오류를 사용할 수 없기 때문입니다.

가장 기본적인 제네릭 클래스

package com.garinzhang.javabase.generic.e1;
/**
* 最基本的泛型类,类型由自己定义
* @author Garin Zhang
*
* @param <T>
*/
public class Point<T> {
private T var;
public T getVar() {
return var;
}
public void setVar(T var) {
this.var = var;
}
}
package com.garinzhang.javabase.generic.e1;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Point<String> p = new Point<String> ();
p.setVar("coder");
System.out.println(p.getVar());
}
}

여러 제네릭 유형

package com.garinzhang.javabase.generic.e2;
/**
* 多个泛型类型,一般多个最好是以靠近T的字母,如S,R等
* @author Garin Zhang
*
* @param <T>
* @param <S>
*/
public class Notepad<T, S> {
private T key;
private S value;
public T getKey() {
return this.key;
}
public S getValue() {
return this.value;
}
public void setKey(T key) {
this.key = key;
}
public void setValue(S value) {
this.value = value;
}
}
package com.garinzhang.javabase.generic.e2;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Notepad<String, Integer> p = new Notepad<String, Integer> ();
p.setKey("coder");
p.setValue(99999);
System.out.println("key: " + p.getKey());
System.out.println("value: " + p.getValue());
}
}

메서드 매개변수에 와일드카드 "?" 사용

package com.garinzhang.javabase.generic.e3;
/**
* 该例子关键在main方法里
* @author Garin Zhang
*
* @param <T>
*/
public class Info<T> {
private T key;
public T getKey() {
return this.key;
}
public void setKey(T key) {
this.key = key;
}
@Override
public String toString() {
return this.key.toString();
}
}
package com.garinzhang.javabase.generic.e3;
/**
* 在方法参数中使用通配符
* @author Garin Zhang
*
*/
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info<String> i = new Info<String>();
i.setKey("coder");
fun(i);
Info<Integer> j = new Info<Integer>();
j.setKey(9999);
fun(j);
}
public static void fun(Info<?> temp) {
System.out.println("Content: " + temp);
}
}

업캐스트 실패

package com.garinzhang.javabase.generic.e4;
/**
* 该例子关键在main方法里
* @author Garin Zhang
*
* @param <T>
*/
public class Info<T> {
private T key;
public T getKey() {
return this.key;
}
public void setKey(T key) {
this.key = key;
}
@Override
public String toString() {
return this.key.toString();
}
}
package com.garinzhang.javabase.generic.e4;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info<String> strEg = new Info<String>();
Info<Object> objEg;
// 编译错误"Type mismatch: cannot convert from Info<String> to Info<Object>"
// 向上转型失败,String -> Object
// objEg = strEg;
}
}

인터페이스에서 제네릭 사용

package com.garinzhang.javabase.generic.e5;
/**
* 该例子关键在main方法里
* @author Garin Zhang
*
* @param <T>
*/
interface Info<T> {
public T getVar();
}
package com.garinzhang.javabase.generic.e5;
/**
* 泛型类
* @author Garin Zhang
*
* @param <T>
*/
public class InfoImpl<T> implements Info<T> {
private T var;
public InfoImpl(T var) {
this.setVar(var);
}
public void setVar(T var) {
this.var = var;
}
public T getVar() {
return this.var;
}
}
package com.garinzhang.javabase.generic.e5;
/**
* 非泛型类
* @author Garin Zhang
*
* @param <T>
*/
public class InfoImpl1 implements Info<String> {
private String var;
public InfoImpl1(String var) {
this.setVar(var);
}
public void setVar(String var) {
this.var = var;
}
public String getVar() {
return this.var;
}
}
package com.garinzhang.javabase.generic.e5;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info<String> strEg = new InfoImpl<String>("coder");
System.out.println("Content: " + strEg.getVar());
Info<String> strEg1 = new InfoImpl1("coder1");
System.out.println("Content: " + strEg1.getVar());
}
}

와일드카드 및 확장, super

package com.garinzhang.javabase.generic.e6;
/**
* 该例子关键在main方法里
* @author Garin Zhang
*
* @param <T>
*/
public class Info<T> {
private T key;
public T getKey() {
return this.key;
}
public void setKey(T key) {
this.key = key;
}
@Override
public String toString() {
return this.key.toString();
}
}
package com.garinzhang.javabase.generic.e6;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info<String> strEg = new Info<String>();
strEg.setKey("coder");
// 编译报错"The method fun(Info<? extends Number>) in the type GenericExample is not applicable for the arguments (Info<String>)"
// upTypeLimit(i);
// 使用Integer,Number类型均可以
Info<Integer> intEg = new Info<Integer>();
intEg.setKey(9999);
upTypeLimit(intEg);
// 编译报错"The method downTypeLimit(Info<? super String>) in the type GenericExample is not applicable for the arguments (Info<Integer>)"
// downTypeLimit(intEg);
 
// 由于使用的是super,downTypeLimit只能接收String本身和Object
// 查看了String的继承关系,没有继承其他类,只有Object
downTypeLimit(strEg);
 
Info<Object> objEg = new Info<Object>();
objEg.setKey(999);
downTypeLimit(objEg);
}
/**
* <? extends T> 表示类型的上界,表示参数化类型的可能是T 或是 T的子类
* @param temp
*/
public static void upTypeLimit(Info<? extends Number> temp) {
System.out.println("Content: " + temp);
}
 
/**
* <? super T> 表示类型下界(Java Core中叫超类型限定),表示参数化类型是此类型的超类型(父类型),直至Object
* 在此例中,表示T只能为Object或String,因为String只继承于Object
* @param temp
*/
public static void downTypeLimit(Info<? super String> temp) {
System.out.println("Content: " + temp);
}
}

메서드 제네릭 사용, 메서드에서 여러 제네릭

package com.garinzhang.javabase.generic.e7;
/**
* 方法泛型,方法里面多个泛型
* @author Garin Zhang
*
* @param <T>
*/
public class Info {
/**
* 格式:方法修饰付 <以逗号隔开的类型列表>返回值类型方法名(参数列表)
* 例如:public <T, S> T fun(T t, S s)
* @param t
* @param s
* @return
*/
public <T, S> T fun(T t, S s) {
System.out.println(s.toString());
return t;
}
}
package com.garinzhang.javabase.generic.e7;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info info = new Info();
String str = info.fun("coder", "print second generic param");
System.out.println(str);
 
int i = info.fun(30, "print second param again");
System.out.println(i);
}
}

에 전달된 제네릭 유형 또는 메서드에 반환된 값은 메서드 호출 시 설정된 매개변수 유형에 따라 결정됩니다.

package com.garinzhang.javabase.generic.e8;
/**
* extends
* @author Garin Zhang
*
* @param <T>
*/
public class Info<T extends Number> {
private T var;
public T getVar() {
return this.var;
}
public void setVar(T var) {
this.var = var;
}
@Override
public String toString() {
return this.var.toString();
}
}
package com.garinzhang.javabase.generic.e8;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info<Integer> intEg = fun(30); // 这里类型已经确定为Integer
System.out.println(intEg.getVar());
}
/**
* 方法中传入或返回的泛型类型由调用方法时所设置的参数类型决定
* @param param
* @return
*/
public static <T extends Number> Info<T> fun(T param) {
Info<T> temp = new Info<T>();
temp.setVar(param);
return temp;
}
}

메서드에 전달된 두 매개변수 유형을 일관되게 만듭니다

package com.garinzhang.javabase.generic.e9;
/**
* 查看main
* @author Garin Zhang
*
* @param <T>
*/
public class Info<T> {
private T var;
public T getVar() {
return this.var;
}
public void setVar(T var) {
this.var = var;
}
@Override
public String toString() {
return this.var.toString();
}
}
package com.garinzhang.javabase.generic.e9;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Info<String> i1 = new Info<String>();
i1.setVar("Hello");
 
Info<String> i2 = new Info<String>();
i2.setVar("Coder");
 
Info<Integer> i3 = new Info<Integer>();
i3.setVar(999);
 
add(i1, i2);
 
//编译错误"The method add(Info<T>, Info<T>) in the type GenericExample is not applicable for the arguments (Info<String>, Info<Integer>)"
// add(i1, i3);
}
/**
* 方法中传入两个参数类型必须一致
* @param param
* @return
*/
public static <T> void add(Info<T> i1, Info<T> i2) {
System.out.println(i1.getVar() + ":" + i2.getVar());
}
}

일반, 변수 매개변수는 Arguments 개체와 유사합니다. JavaScript

package com.garinzhang.javabase.generic.e10;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Integer i[] = fun(1, 2, 3, 4, 5, 6);
fun2(i);
}
public static <T> T[] fun(T... arg) {
return arg;
}
public static <T> void fun2(T param[]) {
System.out.println("generic array: ");
for(T t : param) {
System.out.println(t + " ,");
}
}
}

일반 중첩: 일반 클래스를 매개변수로 사용합니다. 반환 값 유형에 따라 반환 값을 결정합니다.

package com.garinzhang.javabase.generic.e11;
/**
* 接受两个泛型类型
* @author Garin Zhang
*
* @param <T>
*/
public class Info<T, V> {
private T var;
private V value;
 
public T getVar() {
return this.var;
}
public void setVar(T var) {
this.var = var;
}
 
public V getValue(){
return this.value;
}
public void setValue(V value) {
this.value = value;
}
@Override
public String toString() {
return this.var.toString();
}
}
package com.garinzhang.javabase.generic.e11;
/**
* 接受1个泛型类型
* @author Garin Zhang
*
* @param <T>
*/
public class Demo<S> {
private S info;
public Demo(S info) {
this.setInfo(info);
}
public void setInfo(S info) {
this.info = info;
}
public S getInfo() {
return this.info;
}
}
package com.garinzhang.javabase.generic.e11;
import java.util.List;
import com.google.common.collect.Lists;
public class GenericExample {
/**
* @param args
*/
public static void main(String[] args) {
Demo<Info<String, Integer>> d;
Info<String, Integer> i;
i = new Info<String, Integer>();
i.setVar("Coder");
i.setValue(999);
d = new Demo<Info<String,Integer>>(i);
System.out.println("Content: " + d.getInfo().getVar());
System.out.println("Content: " + d.getInfo().getValue());
System.out.println(query(1, 2, 3, 4, 5).toString()); // [1, 2, 3, 4, 5]
// 警告"Type safety: A generic array of Object&Comparable<?>&Serializable is created for a varargs parameter"
System.out.println(query(1, 2, 3, "StringType").toString()); // [1, 2, 3, StringType]
System.out.println(query("I ", "am ", "a ", "coder").toString());// [I , am , a , coder]
 
List<String> list = Lists.newArrayList("I ", "am ", "a ", "coder");
System.out.println(list.toString()); // [I , am , a , coder]
}
/**
* 通过返回值确定泛型类型,这个方法里面的返回值类型,是由方法的定义自动生成的
* @param elements
* @return
*/
public static <E> List<E> query(E... elements) {
// https://github.com/exitsoft/exit-web-framework/commit/1d2f1098a2a4b6abab175b793e2308aa8bd0ea16.
// import com.google.common.collect.Lists;
// <dependency>
// <groupId>com.google.guava</groupId>
// <artifactId>guava</artifactId>
// <version>16.0.1</version>
// </dependency>
return Lists.newArrayList(elements);
}
}

추가 Java 제네릭 학습 예제와 관련된 기사는 PHP를 참조하세요. 중국사이트!

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.