фильтр и использование списка вида наборы Google

Предположим, что у меня есть список (или Набор):

List<String> testList = Lists.newArrayList("assocX","srcT","destA","srcX", "don't care Y", "garbage", "srcB");

Я хотел бы возвратить ImmutableList (Набор), который виды/группы называют в естественном порядке, где условия, которые начинаются с "src", являются первыми, второй "помощник" и "dest" в последний раз. Если термин не содержит их тогда, он должен быть удален из получающегося списка.

Поэтому результатом здесь является "srcB", "srcT", "assocX", "destA".

Я думаю, что могу сделать это с некоторой комбинацией Iterables.filter или Предикатов, но просто не наблюдения его. Должен быть сжатый способ сделать его, я думаю.

Править: Набор вместо списка работает также.

27
задан harschware 22 February 2010 в 18:11
поделиться

4 ответа

Я предлагаю хранить интеллектуальные указатели на исходные данные в каждом векторе . std:: vector позволяет предоставить различные методы сортировки. Кроме того, смарт-указатели будут уничтожаться автоматически при удалении всех ссылок на предмет.

-121--2925015-

Пример IOCPPool для Synapse доступен в разделе Предоставленные файлы .

-121--3453491-

Пока эти три префикса являются единственными вещами, которые вас волнуют, я бы предложил что-то подобное:

    Predicate<String> filter = new Predicate<String>() {
        @Override
        public boolean apply(String input) {
            return input.startsWith("src") || input.startsWith("assoc") || input.startsWith("dest");
        }
    };

    Function<String, Integer> assignWeights = new Function<String, Integer>() {
        @Override
        public Integer apply(String from) {
            if (from.startsWith("src")) {
                return 0;
            } else if (from.startsWith("assoc")) {
                return 1;
            } else if (from.startsWith("dest")) {
                return 2;
            } else {
                /* Shouldn't be possible but have to do something */
                throw new IllegalArgrumentException(from + " is not a valid argument");
            }
        }
    };

    ImmutableList<String> sortedFiltered = ImmutableList.copyOf(
            Ordering.natural().onResultOf(assignWeights).sortedCopy(
                    Iterables.filter(testList, filter)
            )
    );

Это решение определенно не будет невероятно хорошо масштабироваться, если вы начнете добавлять дополнительные префиксы для фильтрации или сортировки, так как вам придется постоянно обновлять и фильтр, и вес каждого префикса.

33
ответ дан 28 November 2019 в 05:17
поделиться

Посмотрите на этот пример Google Collections.

Function<Fruit, String> getNameFunction = new Function<Fruit, String>() {
    public String apply(Fruit from) {
        return from.getName();
    }
};

Ordering<Fruit> nameOrdering = Ordering.natural().onResultOf(getNameFunction);

ImmutableSortedSet<Fruit> sortedFruits = ImmutableSortedSet.orderedBy(
    nameOrdering).addAll(fruits).build();

Хотя это, конечно, возвращает множество.

12
ответ дан 28 November 2019 в 05:17
поделиться

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

0
ответ дан 28 November 2019 в 05:17
поделиться

Обычно подобная сортировка четко различающихся данных - плохой дизайн. В вашем случае, когда вы говорите «assocX», «assoc» имеет значение, отличное от «X», но вы объединяете их вместе.

Поэтому я предлагаю создать класс с двумя полями. Затем вы можете создать порядок в первом поле, другой - во втором, и объединить их (например, Ordering # complex ()). С помощью метода toString (), который объединяет эти поля в строку. В качестве бонуса это может значительно снизить использование памяти за счет совместного использования.

Таким образом, вы должны сортировать список таких объектов, и если бы вы хотели их распечатать, вы бы просто вызывали для них toString ().

0
ответ дан 28 November 2019 в 05:17
поделиться
Другие вопросы по тегам:

Похожие вопросы: