带for循环的Java搜索数组无法找到所有结果

时间:2018-08-10 07:30:38

标签: java string loops for-loop search

我正在使用Java构建Android应用程序,并且正在尝试构建搜索功能以从列表视图中查找结果。 到目前为止,我已经设法使搜索功能起作用,但是它不能正常工作-它只能找到特定条件。例如,它找到TC产品名称,JC产品名称,但没有找到产品名称。 而且,如果我尝试查找某些字符串值,似乎也找不到所有值。

这是我的代码:

package com.example.user.sortiment;

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.Filter;
import android.widget.Filterable;
import android.widget.TextView;

import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

/**
 * Created by user on 11.05.2018
 */

public class SortimentAdapter extends BaseAdapter {

LayoutInflater mInflator;
List<Sortiment> map;
List<Sortiment> filterMap;

    public void performFiltering(CharSequence constraint) {

        String filterString = constraint.toString().toLowerCase();
        if (Objects.equals(filterString, "")) {
            filterMap = map;
            notifyDataSetChanged();
            return;
        }

        int count = map.size();
        filterMap = new ArrayList<Sortiment>(count);

        Sortiment filterableSortiment ;

        for (int i = 0; i < count; i++) {
            filterableSortiment = map.get(i);
            if 
(filterableSortiment.name.toLowerCase().contains(filterString)) {
                filterMap.add(filterableSortiment);
            }
        }

        notifyDataSetChanged();

    }

public SortimentAdapter(Context c, List<Sortiment> inputMap) {
    mInflator = (LayoutInflater) 
c.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    map = inputMap;
    filterMap = inputMap;
}

@Override
public int getCount() {
    return filterMap.size();
}

@Override
public Object getItem(int position) {
    return filterMap.get(position);
}

@Override
public long getItemId(int position) {
    return position;
}

@Override
public View getView(int position, View convertView, ViewGroup parent) {

    View v = mInflator.inflate(R.layout.item_layout,null);
    TextView nameTextView = (TextView) v.findViewById(R.id.nameTextView);
    TextView priceTextView = (TextView) v.findViewById(R.id.priceTextView);

    Sortiment viewObject = filterMap.get(position);
    nameTextView.setText(viewObject.name);
    //priceTextView.setText(String.format("%.0f", prices.get(position)));
    priceTextView.setText(viewObject.ean.toString());

    return v;
}

}

我怀疑存在以下问题:if(filterableSortiment.name.toLowerCase()。contains(filterString)){ ,但我不确定。

有什么想法吗? 谢谢

4 个答案:

答案 0 :(得分:1)

编辑:

现在已经发布了完整的代码,该地图似乎是一个列表。除了一些有关地图工作原理的一般信息外,我下面的解释不应该用于您的示例。

地图,它们如何工作?

您正在地图上进行for,其中的按键可能不一定按顺序排列。

Here是对地图工作方式的说明。

地图是键值对字典,而不是标题中提到的简单列表/数组。

这是我的假设,但我可能错了,但以下一行对我来说很奇怪:

filterableSortiment = map.get(i);

此键通过键i获取,而通过列表中第i的位置获取,因为地图不是列表。

从数学上讲,映射定义为:“元素从一组到另一组的映射。”

如果映射像数组一样线性,请注意,否则,您可能无法到达所有元素。

核心问题:

您使用的map可能没有线性键,并且无法通过简单增加i的for循环来访问。

通过在调试时检查地图来检查地图的结构。

如果您的键值对看起来不像数组:

0 1 2 3 4 5

| | | | | |

A B C D E F

然后您的算法将丢失元素。

例如,如果在地图中使用键2324添加了一些元素,则当您的数量仅为30个元素时,由于地图的键稀​​疏地填充了地图,因此您会错过这一点。

如果您的地图看起来像

1 5 7 8 9 23

| | | | | |

A B C D E F

如果您进行for 0 > map.count

你会去

map.get(0)-不返回任何内容

map.get(1)-返回A

map.get(2)-不返回任何内容

map.get(3)-不返回任何内容

map.get(4)-不返回任何内容

map.get(5)-返回B

如果键的排列顺序不像数组“ map”中的那样,则C, D, E and F元素会丢失。

解决方案:

我建议您在地图上使用适当的迭代器(针对每个循环),而不要使用索引线性增加for的{​​{1}}循环,因为您可能会错过地图上的空白。

请参阅此answer或此answer

后续问题:

  • 您能否提及示例中的i是什么数据类型?

map

答案 1 :(得分:1)

现在,您已经更新了答案,很明显,您的“地图”根本不是地图。因此,这现在无效。将来,请提供足够的信息,以便您的问题得到解答。

public void performFiltering(CharSequence constraint) {

    String filterString = constraint.toString().toLowerCase();
    if (filterString.equals("")) {
        filterMap = map;
        notifyDataSetChanged();
        return;
    }

    int count = map.size();
    filterMap = new ArrayList<Sortiment>(count);

    Sortiment filterableSortiment ;

    for (filterMap.Entry<String, String> entry : filterMap.entrySet())
    {
        filterableSortiment = entry.getValue();
        if (filterableSortiment.name.toLowerCase().contains(filterString)) {
            filterMap.add(filterableSortiment);
        }
    }
    notifyDataSetChanged();
}

答案 2 :(得分:1)

如果您只想过滤“分类”列表中的条目,则建议使用Java 8 Stream API。这将过滤“地图”中的所有条目,并将结果保存在“ filterMap”中。

import java.util.List;
import java.util.stream.Collectors;

public void performFiltering(CharSequence constraint) {
    String filterString = constraint.toString().toLowerCase();

    // Define what to do, if filterString is an empty String
    if(filterString.isEmpty()){
        filterMap = map;
        notifyDataSetChanged();
        return;
    }

    // Filter through the sortiment list
    filterMap = map.stream()
        .filter(s -> s.name.toLowerCase().contains(filterString))
        .collect(Collectors.toList());

    notifyDataSetChanged();
}

答案 3 :(得分:0)

答案隐藏在Android清单中:

android:windowSoftInputMode="stateHidden"

...必须替换为:

android:windowSoftInputMode="adjustPan"