0

I have a very weird problem, And I want to do it extremely efficient way. In my app milliseconds count..

I have four ArrayLists of Strings

title desc, price, usageArray;

The first three contains data where as usageArray contains data and "NONE" at some places e.g

UsageArray

a b c NONE D NONE

etc

I want to remove the "NONE" From usageArray in such a way that e.g let the index of First NONE is 3 then the third element in title, desc and price is also remove.

How can I do this in extremely efficient way

Mattias Isegran Bergander
  • 11,811
  • 2
  • 41
  • 49
Muhammad Umar
  • 11,391
  • 21
  • 91
  • 193
  • Is the data related? Do these elements have key-value relationships? – Makoto Jun 30 '13 at 17:36
  • This (as usual) depends. How big is your data set? Have you tested a basic approach and seen that it takes too much time? Simple LinkedLists for example are efficient when it comes to removal. What do you want to end up with, a data structure that is fast for looking up things in what way? By index? By a key? – Mattias Isegran Bergander Jun 30 '13 at 17:37
  • @Makoto no actually this is a good idea, i can hardcode keys let me try... – Muhammad Umar Jun 30 '13 at 17:37
  • You should write code to do that. There is no automatic way of doing that. Using Set will not solve the problem that you are trying to solve. – Wand Maker Jun 30 '13 at 17:38
  • Again, I thin I'm misunderstanding you. In your code, do you treat any of the lists as keys to any of the others' values? I don't know what you're using these lists for, and if you don't want duplicates in one of them, a Set is the most direct way to do it. Could you clarify your question a bit more with use cases of these lists? – Makoto Jun 30 '13 at 17:39
  • Actually first thee lists contains data of rows and Lets say usageArray contains which rows should be displayed. NONE Will not be displayed. Apparently there is no special built-in code to handle such thing, i am writing something that works. – Muhammad Umar Jun 30 '13 at 17:42

5 Answers5

3

First of all, I'll suggest you to create a class, say, Book, containing all those attributes and have a List<Book>, instead of having 4 different list for all of them.

P.S. : In general, whenever you see yourself modifying or working with multiple Lists in parallel, that is an indication that it's time to create a new class.

class Book {
    String title;
    String desc;
    BigDecimal price;
    String usage;
}

Then you have a list like this:

List<Book> books;

Now, to remove all the indices where usage is NULL, is as easy as:

ListIterator<Book> iterator = books.listIterator();

while (iterator.hasNext()) {
    Book book = iterator.next();
    if (book.getUsage().equals("NULL")) {
        iterator.remove();
    }
} 

Also, wherever you are having "Null" as your string value, you should consider changing it to null.

Note: You should pay attention while removing elements from your List. You should always use an iterator while doing that.

See also:

Community
  • 1
  • 1
Rohit Jain
  • 209,639
  • 45
  • 409
  • 525
0

Try this

   int index = 0;
    for (int i = 0; i < usageArray.size(); i++) {
        if (usageArray.get(i).contains("NONE")) {
            index=usageArray.indexOf("NONE");
            usageArray.remove(index);
            title.remove(index);
            desc.remove(index);
            price.remove(index);
            i--;
        }

    }
Ruchira Gayan Ranaweera
  • 34,993
  • 17
  • 75
  • 115
0

This is tested code. public class mainclass {

public static void main(String ar[])
{

    List<Integer> indexes = new ArrayList<Integer>();


    List<String> title = new ArrayList<String>();
        title.add("title 1");
        title.add("title 2");
        title.add("title 3");
    List<String> desc = new ArrayList<String>();
        desc.add("desc 1");
        desc.add("desc 2");
        desc.add("desc 3");
    List<String> price = new ArrayList<String>();
        price.add("price 1");
        price.add("price 2");
        price.add("price 3");
    List<String> usageArray = new ArrayList<String>();
        usageArray.add("usage 1");
        usageArray.add("NONE");
        usageArray.add("usage 1");


    for (String string : usageArray) {

        if(string.equalsIgnoreCase("NONE"))
        {
            indexes.add(usageArray.indexOf(string));

        }

    }


    for (Integer index : indexes) {

        price.remove(index);
        desc.remove(index);
        title.remove(index);
        usageArray.remove(index);

    }

}

}

Umais Gillani
  • 608
  • 4
  • 9
0

This (as usual) depends. How big is your data set? Have you tested a basic approach and seen that it takes too much time? Simple LinkedLists for example are more efficient (compared to ArrayList) when it comes to removal. What do you want to end up with, a data structure that is fast for looking up things in what way? By index? By a key? What do you need to be fast, the actual filtering or afterwards when you are done?

Multiple ways of doing this even in simple cases. What about merging into into one object with fields for each column:

class Data {
  String title;
  String desc;
  String price;
  String usage;
}

And then:

LinkedList<Data> allData = ...;

for (Iterator iter=allData.iterator();iter.hasNext();) {
  Data data = iter.next();
  if ("NONE".equals(data.usage)) { //see note about using something else here
    iter.remove();
  }
}
//allData is now cleaned of any entries with USAGE of NONE

Usually quicker than if using a ArrayList, certainly quicker than using multiple lists etc etc. But again depends.

Might for example want to have the usage in a separate class depending on your data modelling needs.

For further performance regardless of algorithm (which is the important part so only for fun, always measure!) consider:

  • Make usage an enum or int for more efficient comparison or a String constant so don't need equals(), can instead use usage == NONE
Mattias Isegran Bergander
  • 11,811
  • 2
  • 41
  • 49
-1

check the Following Code,

public static void main(String ar[])
{

    List<String> title = new ArrayList<String>();
        title.add("title 1");
        title.add("title 2");
        title.add("title 3");
    List<String> desc = new ArrayList<String>();
        desc.add("desc 1");
        desc.add("desc 2");
        desc.add("desc 3");
    List<String> price = new ArrayList<String>();
        price.add("price 1");
        price.add("price 2");
        price.add("price 3");
    List<String> usageArray = new ArrayList<String>();
        usageArray.add("usage 1");
        usageArray.add("NONE");
        usageArray.add("usage 1");


    int index = -1;
    for (String string : usageArray) {

        if(string.equalsIgnoreCase("NONE"))
        {
            index = usageArray.indexOf(string);
                    usageArray.remove(string);
                    price.remove(index);
                    desc.remove(index);
                    title.remove(index);

        }

    }





}
Umais Gillani
  • 608
  • 4
  • 9
  • 1
    You can't remove usageArray.remove(string); inside the for loop. you will get the ConcurrentModificationException – Ruchira Gayan Ranaweera Jun 30 '13 at 17:43
  • oh, i forgot, i Think in if(string.equalsIgnoreCase("NONE")) we should only take indexes in another List then by iterating on new list, we can remove index values from other ArrayLists. – Umais Gillani Jun 30 '13 at 17:48