我试图以这种方式合并2个数组:
int[] arr1 = { 1, 3, 9, 5 };
int[] arr2 = { 7, 0, 5, 4, 3 };
现在我需要创建一个如下所示的新数组:
int[] merged = { 1, 3, 9, 5, 7, 0, 4 };
因此我需要将所有数字放在新数组中,但如果两个数组中都有数字,那么它不应该重复,每个数字在merged
数组中只应该只有一次。
在同一个数组中,数字永远不会是两次或更多次。
这是我建立的程序:
int[] arr1 = { 1, 6, -6, -9, 3, 4, -8, -7 };
int[] arr2 = { 5, 3, 2, 1, 70, 6, 7, -9, 99, 81 };
int counter = arr1.length;
boolean b = true;
for (int i = 0; i < arr1.length; i++) {
for (int j = 0; j < arr2.length && b == true; j++) {
if (arr1[i] == arr2[j])
b = false;
}
if (b == true) {
counter++;
}
b = true;
}
System.out.println(counter);
由于某种原因,它不起作用..
我正在尝试编写没有内置函数或列表的程序,谢谢。
答案 0 :(得分:2)
不使用List
或Set
或任何第三方库(准备好Java 101家庭作业):
int[] arr1 = { 1, 6, -6, -9, 3, 4, -8, -7 };
int[] arr2 = { 5, 3, 2, 1, 70, 6, 7, -9, 99, 81 };
// Create a boolean array with the same length as the first array.
boolean[] duplicates = new boolean[arr1.length];
// Counter for how many duplicates we found.
int numDuplicates = 0;
// Loop through the first array and get all duplicates.
for (int i = 0; i < arr1.length; i++) {
boolean duplicate = false;
for (int j = 0; j < arr2.length; j++) {
if (arr1[i] == arr2[j]) {
duplicate = true;
numDuplicates++;
break;
}
}
duplicates[i] = duplicate;
}
// The length of the merged array will be the two lengths subtracted by the number of
// duplicates we found.
int[] mergedArray = new int[arr1.length + arr2.length - numDuplicates];
int index = 0;
// loop through the first array. Don't add it to the merged array if it is a duplicate.
for (int i = 0; i < arr1.length; i++) {
if (!duplicates[i]) {
mergedArray[index] = arr1[i];
index++;
}
}
// loop through the second array and add all items.
for (int i = 0; i < arr2.length; i++) {
mergedArray[index] = arr2[i];
index++;
}
// optional. sort array
Arrays.sort(mergedArray);
System.out.println(Arrays.toString(mergedArray));
输出:
[-9, -8, -7, -6, 1, 2, 3, 4, 5, 6, 7, 70, 81, 99]
使用Set
:
public static int[] mergeArrays(int[] arr1, int[] arr2) {
Set<Integer> set = new HashSet<Integer>();
for (int x : arr1) {
set.add(x);
}
for (int x : arr2) {
set.add(x);
}
int[] result = new int[set.size()];
int index = 0;
for (Iterator<Integer> it = set.iterator(); it.hasNext();) {
result[index] = it.next();
index++;
}
return result;
}
使用List
:
public static int[] mergeArrays(int[] arr1, int[] arr2) {
List<Integer> list = new ArrayList<Integer>();
for (int i = 0, length = arr1.length; i < length; i++) {
list.add(arr1[i]);
}
for (int i = 0, length = arr2.length; i < length; i++) {
if (!list.contains(arr2[i])) {
list.add(arr2[i]);
}
}
int length = list.size();
int[] result = new int[length];
for (int i = 0; i < length; i++) {
result[i] = list.get(i);
}
return result;
}
答案 1 :(得分:1)
在没有找到代码中的错误的情况下,我可以看到你有一个嵌套循环,这意味着运行时间将是O(N ^ 2)。
通过对两个数组O(Nlog(N))进行排序,然后像在合并排序中一样在单个迭代中合并它们,可以获得更好的运行时间,从而消除了过程中的重复项。总运行时间为O(Nlog(N))。
答案 2 :(得分:1)
据我所知,你正试图计算独特的物品。只计算相同的项目。然后添加array1 length和array2 length减去相同的项目数。试试这个:
int [] arr1 = {1,6,-6,-9,3,4,-8,-7};
int [] arr2 = {5,3,2,1,70,6,7,-9,99,81};
int counter = 0;
for(int i=0; i<arr1.length; i++) {
for(int j=0; j<arr2.length; j++) {
Integer a1=arr1[i];
Integer a2=arr2[j];
if( (a1.equals(a2)) ){
counter++;
}
}
}
int counterLast=arr1.length+arr2.length-counter;
System.out.println(counterLast);
答案 3 :(得分:1)
由于您不想要重复,我建议您使用HashSet<Integer>
。
//add elements from both arrays to the set
HashSet<Integer> set = new HashSet<Integer>();
for (int num : arr1)
set.add(new Integer(num));
for (int num : arr2)
set.add(new Integer(num));
// set will have one copy of each of elements in either arr1 and arr2
int[] result = new int[set.size()];
Iterator<Integer> set_iter = set.iterator();
for(int i = 0; set_iter.hasNext(); i++){
result[i] = set_iter.next();
}
return result;
以下是有关HashSet的更多信息:http://docs.oracle.com/javase/7/docs/api/java/util/HashSet.html 这里有关于Iterator的更多信息: http://docs.oracle.com/javase/7/docs/api/java/util/Iterator.html
答案 4 :(得分:1)
虽然你的算法效率非常低,但我认为你的代码中存在逻辑错误,循环块应该是这样的:
for(int i=0; i<arr2.length; i++) {
for(int j=0; j<arr1.length; j++) {
if(arr2[i] == arr1[j]) {
b = false;
break;
}
}
if(b == true) {
counter++;
}
b = true;
}
答案 5 :(得分:1)
根据你的代码,这个程序不能很好地工作,因为两个数组的大小不同,你的外部循环取决于小数组的大小
for(int i = 0; i arr1.length; i ++)
因此当程序达到小数组的大小时程序将结束。所以如果需要这个代码运行良好你需要改变外部(取决于大数组的大小)和内部循环依赖于小数组
int [] arr1 = {1,6,-6,-9,3,4,-8,-7}; int [] arr2 = {5,3,2,1,70,6,7,-9,99,81,55,4};
int counter = arr1.length;
boolean b = true;
for(int i=0; i<arr2.length; i++) {
for(int j=0; j<arr1.length && b==true; j++) {
if(arr2[i] == arr1[j])
{
b = false;
}
}
if(b == true) {
counter++;
}
b = true;
}
System.out.println(counter);
}
}
答案 6 :(得分:1)
//Array copy complexity O(arr1.length + arr2.length)
int arr1Len = arr1.length;
int arr2Len = arr2.length;
int[] both = new int[arr1Len+arr2Len];
int[] result = new int[arr1Len+arr2Len];
System.arraycopy(arr1, 0, both, 0, arr1Len);
System.arraycopy(arr2, 0, both, arr1Len, arr2Len);
//Array sort complexity O(n) < x < O(n lg n)
Arrays.sort(both);
//Sorted array duplication removal O(n)
int counterUnique = 0;
result[0] = both[0];
for (int item : both) {
if(result[counterUnique] != item){
result[++counterUnique]=item;
}
}
//optional
int[] rightSizeResult = Arrays.copyOf(result, counterUnique+1);
哈希集不包含重复项。对于每个值,都会生成散列并用于访问元素 - 对于大多数情况,您可以> 99.99%确定散列是唯一的。 Hashset不维护顺序,要添加它,您可以使用LinkedHashSet。
您无需复制1个数组中的项目,只需
即可Set<Integer> set = new HashSet<Integer>();
set.addAll(Arrays.asList(arr1));
set.addAll(Arrays.asList(arr2));
Integer[] result = set.toArray(new Integer[set.size()]);
Treeset是订单维护集合,没有重复项。
Collection<Integer> result = new TreeSet<Integer>(Arrays.asList(arr1));
result.addAll(Arrays.asList(arr2));
result = Sets.intersection(ImmutableSet.of(arr1), ImmutableSet.of(arr2));
这有几个原因,但最重要的是,您可以减少非atomic操作期间可能发生的潜在问题。在生产代码中,您主要尝试避免原始类型和数组(如果可以)。它们有很强的用例,但这超出了这个问题的范围。
答案 7 :(得分:1)
您可以使用不允许重复元素的SET。我只使用了一个循环。
int[] arr1 = { 1, 6, -6, -9, 3, 4, -8, -7 };
int[] arr2 = { 5, 3, 2, 1, 70, 6, 7, -9, 99, 81 };
int maxLength = arr1.length >= arr2.length ? arr1.length : arr2.length;
Set<Integer> merge = new HashSet<Integer>();
for (int i=0; i<maxLength; i++) {
if (i < arr1.length)
merge.add(arr1[i]);
if (i < arr2.length)
merge.add(arr2[i]);
}
System.out.println(merge.toString());