调用Arrays.asList(arr).contains(value)判断数组是否存在某个元素?

int32位 posted @ Sep 09, 2014 11:50:44 AM in java , 7138 阅读
转载请注明:http://krystism.is-programmer.com/若有错误,请多多指正,谢谢!

这个问题很简单,就是在一个无序数组中判断某个元素是否存在,当然如果自己定义数据结构,可以使用trie,hash,如果不要求完全准确,允许误判,还能使用布隆!显然不能使用二分搜索,因为数组是无序的!当我们要经常搜索时,排序是必要的,或者使用其他数据结构。

这篇文章讨论了下http://www.programcreek.com/2014/04/check-if-array-contains-a-value-java/#more-12168,于是自己测试了下,下面是我的代码(必须使用java8版本以上):

import java.util.*;
interface StringPolicy {
	boolean contains(String[] arr, String value);
}
interface LongPolicy {
	boolean contains(long[] arr, long value);
}
class Policies {
	
    public static boolean useList(String[] arr, String value) {
        return Arrays.asList(arr).contains(value);
    }
    public static boolean useList(long[] arr, long value) {
    	return Arrays.asList(arr).contains(value);
    }
    public static boolean useSet(String[] arr, String value) {
        return new HashSet<>(Arrays.asList(arr)).contains(value);
    }
    public static boolean useSet(long[] arr, long value) {
        return new HashSet<>(Arrays.asList(arr)).contains(value);
    }
    public static boolean useLoop(String[] arr, String value) {
        for (String s : arr) {
            if (s.equals(value))
                return true;
        }
        return false;
    }
    public static boolean useLoop(long[] arr, long value) {
    	for (long l : arr) {
    		if (l == value)
    			return true;
    	}
    	return false;
    }
    public static boolean useStream(String[] arr, String value) {
    	return Arrays.stream(arr).anyMatch(value::equals);
    }
    public static boolean useStream(long[] arr, long value) {
    	return Arrays.stream(arr).anyMatch(l -> l == value);
    }
    public static boolean useParallelStream(String[] arr, String value) {
    	return Arrays.stream(arr).parallel().anyMatch(value::equals);
    }
    public static boolean useParallelStream(long[] arr, long value) {
    	return Arrays.stream(arr).parallel().anyMatch(l -> l == value);
    }
}
public class SearchDemo {
	public static void fill(String[] arr) {
        for(int i = 0; i < arr.length; ++i) {
            arr[i] = String.valueOf(i + 1);
        }
    }
	public static void fill(long[] arr) {
		for (int i = 0; i < arr.length; ++i) {
			arr[i] = i + 1;
		}
	}
	public static void fill(String[] arr, String value) {
		Arrays.fill(arr, value);
	}
	public static void fill(long[] arr, long value) {
		Arrays.fill(arr, value);
	}
	public static void test(String name, StringPolicy p, String[] arr, String value, int times) {
		long start = System.nanoTime();
		for (int i = 0; i < times; ++i) {
			p.contains(arr, value);
		}
		long end = System.nanoTime();
		long d = (end - start) / 1_000_000;
		System.out.printf("%s: %d\n", name, d);
	}
	public static void test(String name, LongPolicy p, long[] arr, long value, int times) {
		long start = System.nanoTime();
		for (int i = 0; i < times; ++i) {
			p.contains(arr, value);
		}
		long end = System.nanoTime();
		long d = (end - start) / 1_000_000;
		System.out.printf("%s: %d\n", name, d);
	}
	public static void main(String[] args) {
		String[] arr1 = new String[10_000];
		long[] arr2 = new long[10_000];
		fill(arr1);
		fill(arr2);
		System.out.println("******************* String **************************");
		test("useLoop", Policies::useLoop, arr1, "A", 10_000);
		test("useList", Policies::useList, arr1, "A", 10_000);
		test("useSet", Policies::useSet, arr1, "A", 10_000);
		test("useStream", Policies::useStream, arr1, "A", 10_000);
		test("useParallelStream", Policies::useParallelStream, arr1, "A", 10_000);
		System.out.println("******************* Long **************************");
		test("useLoop", Policies::useLoop, arr2, -1, 10_000);
		test("useList", Policies::useList, arr2, -1, 10_000);
		test("useSet", Policies::useSet, arr2, -1, 10_000);
		test("useStream", Policies::useStream, arr2, -1, 10_000);
		test("useParallelStream", Policies::useParallelStream, arr2, -1, 10_000);
	}

结果输出是:

数组大小为1k时的结果:
******************* String **************************
useLoop: 141
useList: 128
useSet: 859
useStream: 331
useParallelStream: 746
******************* Long **************************
useLoop: 87
useList: 7
useSet: 40
useStream: 311
useParallelStream: 835
数组大小为10k时的结果:
******************* String **************************
useLoop: 887
useList: 1005
useSet: 7889
useStream: 2489
useParallelStream: 2420
******************* Long **************************
useLoop: 644
useList: 10
useSet: 24
useStream: 2455
useParallelStream: 2748
当把数组大小提高到100k时,结果为:
******************* String **************************
useLoop: 10584
useList: 11597
useSet: 92295
useStream: 31249
useParallelStream: 17176
******************* Long **************************
useLoop: 6167
useList: 10
useSet: 33
useStream: 22633
useParallelStream: 21192
 
可以看出使用字符串时,使用循环的方式会比其他方式更快,但当判断基本数据类型时,使用List是最快的,往往使用Set都不是好方法,使用Stream也并没有提高速率。原文并没有说明!
 
转载请注明:http://krystism.is-programmer.com/若有错误,请多多指正,谢谢!
  • 无匹配
  • 无匹配
celebrity heights 说:
2023年12月15日 15:07

CG in films show us a new magical world. Have you ever wonder about the real heights of actors who play Hobbits in Lord of the Rings? You can find the answer on celeb height wiki with some clicks.


登录 *


loading captcha image...
(输入验证码)
or Ctrl+Enter