2016-01-26 4 views
1

Я пытаюсь составить список, в котором я бы добавил элементы в свою корзину покупок, после чего он покажет, сколько вхождений предметов есть с помощью HashMap.Подсчет Число вхождений элемента в список

public class ShoppingCart 
{ 
    private ArrayList<Items> ShoppingCart; 

    public ShoppingCart() 
    { 
     ShoppingCart = new ArrayList<Items>(); 
    } 

    public void addItems(Items newItems) 
    { 
     ShoppingCart.add(newItems); 
    } 

    public ArrayList<Items> getShoppingCart() 
    { 
     return ShoppingCart; 
    } 

    public void CheckOut() 
    { 
     for(int i = 0; i < ShoppingCart.size(); i++) 
     { 
       HashMap<String, Integer> itemsMap = new HashMap<String, Integer>(); 
       int a = 1; 

       if (itemsMap.containsKey(ShoppingCart.get(i).getName())) 
       { 
        itemsMap.replace(ShoppingCart.get(i).getName(), a, a++); 
       } 
       else 
       { 
        itemsMap.put(ShoppingCart.get(i).getName(), a); 
       } 
      System.out.println(a +"x "+ShoppingCart.get(i)); 
     } 
    } 

и мои пункты созданы с

public class Items 
{ 
    private String name; 

    public Items (String name) 
    { 
     this.name = name; 
    } 

    public String toString() 
    { 
     return name; 
    } 

    public String getName() 
    { 
     return name; 
    } 

} 

В основном я хотел бы создать товары и добавить их в корзину, а затем ShoppingCart.CheckOut(); мои предметы.

Однако, если добавить 4 "Белый хлеб", как это так,

Items bread = new Items("White Bread"); 

    ShoppingCart ShoppingCart = new ShoppingCart(); 

    ShoppingCart.addItems(bread); 
    ShoppingCart.addItems(bread); 
    ShoppingCart.addItems(bread); 
    ShoppingCart.addItems(bread); 

я

1x White Bread 
1x White Bread 
1x White Bread 
1x White Bread 

вместо

4x White Bread 

Что я делаю не так?

+0

использование '++ a' вместо 'a ++' –

+0

Спасибо всем! Я также заметил, что я печатаю в цикле, который дал мне несколько бесполезных выходов, поэтому я тоже изменил это. Я также решил обменять операторы if и else, но изменив условие if на «нет». Также было изменено на LinkedHashMap, чтобы он был более организованным. – Jinjinbug

+0

Вы также, вероятно, выиграете от того, что ваш ShoppingCart рассмотрит на http://codereview.stackexchange.com, так как есть некоторые проблемы. – hcvst

ответ

5

Изменить

itemsMap.replace(ShoppingCart.get(i).getName(), a, a++); 

в

a = itemsMap.get(ShoppingCart.get(i).getName()); // in order to increment the 
               // current counter value 
itemsMap.replace(ShoppingCart.get(i).getName(), a, ++a); 

Использование пост декремент (a++) не изменяет значения в карте, поскольку a++ возвращает исходное значение a.

Кроме того, HashMap должен быть инициализирован вне цикла. В противном случае он всегда будет содержать только один элемент.

+2

'HashMap itemsMap = new HashMap (); 'должно быть вне цикла, тоже – pL4Gu33

+1

Кроме того,' a = 1' означает, что он будет только увеличиваться до 2, никогда 3 или 4. Нужно сначала получить значение с карты, а затем увеличить его. – guitarsteve

+0

@ pL4Gu33 Хорошая точка. Спасибо – Eran

0

сосчитать их заранее и напечатать сумму:

Map<String, Integer> itemsMap = new LinkedHashMap<String, Integer>();  
    for(int i = 0; i < ShoppingCart.size(); i++) 
    { 

      itemsMap.merge(ShoppingCart.get(i).getName(), 1, (old, set) -> old+set); 
    } 

    for (Map.Entry <String, Integer> e: itemsMap.entrySet()) { 
     System.out.println(e.getValue()+"x "+e.getKey()); 
    } 
0

2 основные проблемы: - HashMap создается на каждой итерации, так что вы потеряете все, что вы имели в карте раньше. - Ваш системный вывод в FOR, так что вы получите столько строк, которые будут напечатаны как элементы, которые у вас есть в цикле.

Почему бы не использовать карту для хранения таких предметов?

public class ShoppingCart { 

Map<Items, Integer> shoppingCart = new HashMap<>(); 

public ShoppingCart() { 
} 

public void addItems(Items newItem) { 
    int count = shoppingCart.containsKey(newItem) ? shoppingCart.get(newItem) : 0; 
    shoppingCart.put(newItem, ++count); 
} 

public List<Items> getShoppingCart() { 
    return shoppingCart.keySet() 
     .stream() 
     .flatMap(item -> Collections.nCopies(shoppingCart.get(item), item).stream()) 
     .collect(Collectors.toList()); 
} 

public void CheckOut() { 
    for (Map.Entry<Items, Integer> entry : shoppingCart.entrySet()) { 
     System.out.println(String.format("%dx %s", entry.getValue(), entry.getKey().getName())); 
    } 
} 

public static class Items 
{ 
    private String name; 

    public Items (String name) 
    { 
     this.name = name; 
    } 

    public String toString() 
    { 
     return name; 
    } 

    public String getName() 
    { 
     return name; 
    } 

    @Override 
    public int hashCode() { 
     return name.hashCode(); 
    } 

    @Override 
    public boolean equals(Object obj) { 
     if(obj instanceof Items) { 
      return name.equals(((Items)obj).getName()); 
     } 
     return false; 
    } 
} 

public static void main(String[] args) { 
    Items bread = new Items("White Bread"); 

    ShoppingCart ShoppingCart = new ShoppingCart(); 

    ShoppingCart.addItems(bread); 
    ShoppingCart.addItems(bread); 
    ShoppingCart.addItems(bread); 
    ShoppingCart.addItems(bread); 

    ShoppingCart.CheckOut(); 
    System.out.println(ShoppingCart.getShoppingCart()); 
} 

}

0

Я считаю, что ваша проблема в том, что вы создаете новый HashMap для каждого элемента в список покупок, попробуйте вместо этого:

public void CheckOut() 
{ 
    HashMap<String, Integer> itemsMap = new HashMap<String, Integer>(); 
    for(int i = 0; i < ShoppingCart.size(); i++) 
    { 
     if (itemsMap.containsKey(ShoppingCart.get(i).getName())) 
     { 
      itemsMap.put(ShoppingCart.get(i).getName(), itemsMap.get(ShoppingCart.get(i).getName())+1); 
     } 
     else 
     { 
      itemsMap.put(ShoppingCart.get(i).getName(), 1); 
     } 
    } 
    Iterator it = itemsMap.entrySet().iterator(); 
    while (it.hasNext()) { 
     Map.Entry pair = (Map.Entry)it.next(); 
     System.out.println(pair.getValue()+"x " + pair.getKey()); 
    } 
}