Finding the same elements in an array and preventing duplicate counting - java

Given the following code:
public static int countSames(Object[] a) {
int count = 0;
for (int i = 0; i < a.length; i++) {
for (int k = 0; k < a.length; k++) {
if (a[i].equals(a[k]) && i != k) {
count += 1;
break; //Preventing from counting duplicate times, is there way to replace this?
}
}
}
return count;
}
I would like to know if there is a solution which doesn't use break statement since I've heard its bad practice.
But without the break this method returns 6 instead of wanted 3 for array {'x', 'x', 'x'}.

If you're trying to find the number of unique elements in the array try using this approach as it has only one loop and hence efficient.
private static int findNUmberOfUnique(String[] array) {
Set<String> set=new HashSet<>();
for(int i=0;i<array.length;i++){
if(!set.contains(array[i])){
set.add(array[i]);
}
}
return set.size();
}
Let me know if I did not understand your requirement clearly.

You can always use a flag instead of break:
public static int countSames(Object[] a) {
int count = 0;
for (int i = 0; i < a.length; i++) {
boolean found = false;
for (int k = 0; k < a.length && !found; k++) {
if (a[i].equals(a[k]) && i != k) {
count += 1;
found = true;
}
}
}
return count;
}

You can use a hashmap to find the same elements in an array and preventing duplicate counting.
class Solution {
public int[] intersection(int[] nums1, int[] nums2) {
HashSet<Integer>hs=new HashSet<Integer>();
for(int i:nums1)
hs.add(i);
HashSet<Integer>hs1=new HashSet<Integer>();
for(int j:nums2){
if(hs.contains(j)){
hs1.add(j);
}
}
int[] res=new int[hs1.size()];
int j=0;
for(int k:hs1)
res[j++]=k;
return res;
}
}

Related

Why does my Arraylist keep printing [3,2]?

I'm trying to remove every instance of value from an array of integers, and return the length of the new array of integers.The input is [3,2,2,3], with val being 3. The output should be [2,2], with length 2. I keep getting [3,2], but I am removing val through an array.
class Solution {
public int removeElement(int[] nums, int val) {
ArrayList<Integer> list = new ArrayList<Integer>();
for(int i = 0; i < nums.length; i++) {
list.add(nums[i]);
}
if(list.isEmpty()) {
return 0;
}
for(int i = 0; i < list.size(); i++) {
if(list.get(i) == val) {
list.remove(i);
}
}
return list.size();
}
}
When you remove the first 3 you will have i=0 and next the array list will resize, so when you delete you need to do i - -.
class Solution {
public int removeElement(int[] nums, int val) {
ArrayList<Integer> list = new ArrayList<Integer>();
for(int i = 0; i < nums.length; i++) {
list.add(nums[i]);
}
if(list.isEmpty()) {
return 0;
}
for(int i = 0; i < list.size(); i++) {
if(list.get(i) == val) {
list.remove(i);
i--;
}
}
return list.size();
}
}
You haven’t shown any printing code but I assume you print nums based on the number returned by this method. That means you never change nums in any way and just print the first n numbers from there. You need to return the modified array instead of just the length.
You do not need to call remove at all (while removing like you do, it is okay, but for example, if you do this in a foreach cycle, it would crash on ConcurrentModificationException. Instead, you can determine whether to add item to the resulting list or not inside the first for loop (which is in my opinion safer):
ArrayList<Integer> list = new ArrayList<Integer>();
for(int i = 0; i < nums.length; i++) {
if (nums[i] != val) {
list.add(nums[i]);
}
}
return list.size();
(I know that this does not answer your question directly)

Use indexOf for 2D array in java

Hello I create a 2D array and i want to find the position from the first 2 in the array. And after to add the index in a new ArrayList. But this code doesn't work. Any idea for the problem?
import java.util.ArrayList;
class Test {
public static void main(String[] args) {
ArrayList<Integer> tableau = new ArrayList<Integer>();
int[][] tab = {
{1,1,1,1,1,1,2,1,1,2,1,1,1,2,1,2,1,1,1,1,1},
{1,1,1,1,1,1,1,1,2,1,1,1,1,1,1,1,1,1,1,1,1},
};
for (int i = 0; i < tab.length; i++) {
int j = tab[i].indexOf(2);
for (int k = j ; k < tab[i].length; k++) {
if (tab[i][j] == 2){
tableau.add(j);
}
}
}
for (Integer row : tableau) {
System.out.println("row = "+ Arrays.toString(tableau));
}
}
}
As others have mentioned, regular arrays do not have an indexOf method, meaning that you will get an error when you compile.
However, you can easily create your own method to use as a substitute.
private static int indexOf(int value, int[] array)
{
for (int i=0; i<array.length; i++)
{
if (array[i] == value)
return i;
}
return -1;
}
Then you can just replace this line:
int j = tab[i].indexOf(2);
With this one:
int j = indexOf(2, tab[i]);

How do I remove duplicates from two arrays?

I need to have an algorithm that changes values in one array if it is in the second array. The result is that the first array should not have any values that are in the second array.
The arrays are of random length (on average ranging from 0 to 15 integers each), and the content of each array is a list of sorted numbers, ranging from 0 to 90.
public void clearDuplicates(int[] A, int[] B){
for(int i = 0; i < A.length; i++){
for(int j = 0; j < B.length; j++)
if(A[i] == B[j])
A[i]++;
}
}
My current code does not clear all of the duplicates. On top of that it might be possible it will creat an index out of bounds, or the content can get above 90.
Although your question is not very clear, this might do the job. Assumptions:
The number of integers in A and B is smaller than 90.
The array A is not sorted afterwards (use Arrays.sort() if you wish to
fix that).
The array A might contain duplicates within itself afterwards.
public void clearDuplicates(int[] A, int[] B) {
// Initialize a set of numbers which are not in B to all numbers 0--90
final Set<Integer> notInB = new HashSet<>();
for (int i = 0; i <= 90; i++) {
notInB.add(i);
}
// Create a set of numbers which are in B. Since lookups in hash set are
// O(1), this will be much more efficient than manually searching over B
// each time. At the same time, remove elements which are in B from the
// set of elements not in B.
final Set<Integer> bSet = new HashSet<>();
for (final int b : B) {
bSet.add(b);
notInB.remove(b);
}
// Search and remove duplicates
for (int i = 0; i < A.length; i++) {
if (bSet.contains(A[i])) {
// Try to replace the duplicate by a number not in B
if (!notInB.isEmpty()) {
A[i] = notInB.iterator().next();
// Remove the added value from notInB
notInB.remove(A[i]);
}
// If not possible, return - there is no way to remove the
// duplicates with the given constraints
else {
return;
}
}
}
}
You can do it just by using int[ ] although it's a bit cumbersome. The only constraint is that there may not be duplicates within B itself.
public void clearDuplicates(int[] A, int[] B) {
//Number of duplicates
int duplicate = 0;
//First you need to find the number of duplicates
for (int i = 0; i < A.length; i++) {
for (int j = 0; j < B.length; j++)
if (A[i] == B[j])
duplicate++;
}
//New A without duplicates
int[] newA = new int[A.length-duplicate];
//For indexing elements in the new A
int notDuplicate = 0;
//For knowing if it is or isn't a duplicate
boolean check;
//Filling the new A (without duplicates)
for (int i = 0; i < A.length; i++) {
check = true;
for (int j = 0; j < B.length; j++) {
if (A[i] == B[j]) {
check = false;
notDuplicate--;//Adjusting the index
}
}
//Put this element in the new array
if(check)
newA[notDuplicate] = A[i];
notDuplicate++;//Adjusting the index
}
}
public class DuplicateRemove {
public static void main(String[] args) {
int[] A = { 1, 8, 3, 4, 5, 6 };
int[] B = { 1, 4 };
print(clear(A, B));
}
public static int[] clear(int[] A, int[] B) {
int a = 0;
for (int i = 0; i < A.length; i++) {
for (int j = 0; j < B.length; j++) {
if (A[i] == B[j]) {
a++;
for (int k = i; k < A.length - a; k++) {
A[k] = A[k + 1];
}
}
}
}
int[] C = new int[A.length - a];
for (int p = 0; p < C.length; p++)
C[p] = A[p];
return C;
}
public static void print(int[] A) {
for (int i = 0; i < A.length; i++)
System.out.println("Element: " + A[i]);
}
}
Here is an example.. I compiled and its working. For any question just let me know :)
maybe you should try the following code:
public void clear (int[] A, int[] B)
{
for (int i=0; i<A.length;i++)
{
for (int j=0; j<B.length; j++)
if(A[i]==B[j])
{
for (int k=i; k<A.length;k++)
A[k]=A[k+1];
j=B.length-1; //so that the cycle for will not be executed
}
}
}

finding distinct elements of an unsorted string array

i have an array of strings, it is unsorted and it has duplicate elements. i want to count the distinct elements,but when i call my method it returns number of all elements, not just the distinct ones. any idea please?
public static double countDistinctString(String[] array) {
double distinctStrings = 0;
for (int j = 0; j < array.length; j++){
String thisString = array[j];
boolean seenThisStringBefore = false;
for (int i = 0; i < j; i++){
if (thisString == array[i]){
seenThisStringBefore = true;
}
}
if (!seenThisStringBefore){
distinctStrings++;
}
}
return distinctStrings;
}
}
The problem is that you're using == to compare strings; see How do I compare strings in Java? for why this doesn't work. Use if (thisString.equals(array[i])) instead.
This should work (I've also improved it a bit - using int instead of double, using break once found the match):
public static double countDistinctString(String[] array) {
int distinctStrings = 0;
for (int j = 0; j < array.length; j++) {
String currentString = array[j];
boolean seenThisStringBefore = false;
for (int i = 0; i < j; i++){
if (currentString.equals(array[i])) {
seenThisStringBefore = true;
break;
}
}
if (!seenThisStringBefore) {
distinctStrings++;
}
}
return distinctStrings;
}

Finding uniques integers in an array

i have an array of integers like this one :
A={1,1,4,4,4,1,1}
i want to count the each number once , for this example the awnser is 2 becuase i want to count 1 once and 4 once
i dont want to use sorting methods
i am unable to find a way to solve it using java.
i did this but it gives me 0
public static void main(String args[]) {
int a[] = { 1,1,4,4,4,4,1,1};
System.out.print(new Test4().uniques(a));
}
public int uniques(int[] a) {
int unique = 0;
int tempcount = 0;
for (int i = 0; i < a.length; i++) {
for (int j = 0; j < a.length; j++) {
if (a[i] == a[j]) {
tempcount++;
}
}
if (tempcount <= 2) {
unique=a[i];
}
tempcount = 0;
}
return unique;
}
the purpose of the question is to understand the logic of it but not solving it using ready methods or classes
This one should work. I guess this might be not the most elegant way, but it is pretty straightforward and uses only simple arrays. Method returns number of digits from array, but without counting duplicates - and this I believe is your goal.
public int uniques(int[] a) {
int tempArray[] = new int[a.length];
boolean duplicate = false;
int index = 0;
int digitsAdded = 0;
for (int i = 0; i < a.length; i++) {
for (int j = 0; j < tempArray.length; j++) {
if (a[i] == tempArray[j]) {
duplicate = true;
}
}
if(!duplicate) {
tempArray[index] = a[i];
index++;
digitsAdded++;
}
duplicate = false;
}
//this loop is needed if you have '0' in your input array - when creating temp
//array it is filled with 0s and then any 0 in input is treated as a duplicate
//again - not most elegant solution, maybe I will find better later...
for(int i = 0; i < a.length; i++) {
if(a[i] == 0) {
digitsAdded++;
break;
}
}
return digitsAdded;
}
Okay first of all in your solution you are returning the int unique, that you are setting as the value that is unique a[i]. So it would only return 1 or 4 in your example.
Next, about an actual solution. You need to check if you have already seen that number. What you need to check is that for every number in the array is only appears in front of your position and not before. You can do this using this code below.
public int uniques(int[] a) {
int unique = 1;
boolean seen = false;
for (int i = 1; i < a.length; i++) {
for (int j = 0; j < i; j++) {
if (a[i] == a[j]) {
seen = true;
}
}
if (!seen) {
unique++;
}
seen = false;
}
return unique;
}
In this code you are iterating over the number you have seen and comparing to the number you are checking (a[i]). You know that for it to be unique you cant have seen it before.
I see two possible solutions:
using set
public int unique(int[] a) {
Set<Integer> set = new HashSet<>();
for (int i : a) {
set.add(i);
}
return set.size();
}
using quick sort
public int unique(int[] a) {
Arrays.sort(a);
int cnt = 1;
int example = a[0];
for (int i = 1; i < a.length; i++) {
if (example != a[i]) {
cnt++;
example = a[i];
}
}
return cnt;
}
My performance tests say that second solution is faster ~ 30%.
if restricted to only arrays, consider trying this:
Lets Take a temporary array of the same size of orignal array, where we store each unique letter and suppose a is your orignal array,
int[] tempArray= new int[a.length];
int tempArraycounter = 0;
bool isUnique = true;
for (int i = 0; i < a.length; i++)
{
isUnique = true;
for (int j = 0; j < tempArray.length; j++)
{
if(tempArray[j] == a[i])
isUnique = false;
}
if(isUnique)
{
tempArray[tempArraycounter] = a[i];
tempArraycounter++;
isUnique = false;
}
}
now tempArraycounter will be your answer ;)
Try Following code:
int test[]={1,1,4,4,4,1,1};
Set<Integer> set=new LinkedHashSet<Integer>();
for(int i=0;i<test.length;i++){
set.add(test[i]);
}
System.out.println(set);
Output :
[1, 4]
At the end set would contain unique integers.

Categories

Resources