Страница 1 из 1

Количество повторяющихся чисел в списке

Добавлено: Сб окт 13, 2012 9:37 am
berg
Массив случайных чисел от 1 до 1000 представлен в виде списка.
Как составить программу, чтобы на экран выводились числа в порядке их возрастания и одновременно указывалось количество повторяющихся чисел?
Заранее благодарен.

Добавлено: Сб окт 13, 2012 10:44 am
Selin
> p:=rand(1..200): k:=1000: L:=sort([seq(p(),k=1..k)]): L;

> H:=[op({op(ListTools[FindRepetitions](L))})]: seq([H[t],ListTools[Occurrences](H[t],L)],t=1..nops(H));

Далее уж сами легко домислите, получая все, что нужно и даже более.

Добавлено: Сб окт 13, 2012 1:44 pm
berg
Спасибо, Selin. Интересная процедура, но я не могу домыслить, как ее применить к какому-то конкретному списку, например:
(67,19,4,90,1,5, 32,90,5,5,321).

Добавлено: Сб окт 13, 2012 2:54 pm
Selin
> L:=[67, 19, 4, 90, 1, 5, 32, 90, 5, 5, 321];
L := [67, 19, 4, 90, 1, 5, 32, 90, 5, 5, 321]
> H:=[op({op(ListTools[FindRepetitions](L))})]: seq([H[t],ListTools[Occurrences](H[t],L)],t=1..nops(H));
[5, 3], [90, 2]

Добавлено: Сб окт 13, 2012 7:27 pm
berg
Процедура работает, но есть один недостаток: не указываются числа, которые повторяются один раз или которых нет совсем. Это искажает общий результат. Числа, повторяющиеся один раз, необходимо указывать.
Можно ли исправить этот недостаток?

Модификация

Добавлено: Сб окт 13, 2012 8:53 pm
Markiyan Hirnyk
berg писал(а):Процедура работает, но есть один недостаток: не указываются числа, которые повторяются один раз или которых нет совсем. Это искажает общий результат. Числа, повторяющиеся один раз, необходимо указывать.
Можно ли исправить этот недостаток?

with(ListTools):
L := [67, 19, 4, 90, 1, 5, 32, 90, 5, 5, 321];

[67, 19, 4, 90, 1, 5, 32, 90, 5, 5, 321]
{seq([x, Occurrences(x, L)], x = L)};
{[1, 1], [4, 1], [5, 3], [19, 1], [32, 1], [67, 1], [90, 2],[321, 1]}
convert(%, list);
[[1, 1], [4, 1], [5, 3], [19, 1], [32, 1], [67, 1], [90, 2],[321, 1]]

Добавлено: Сб окт 13, 2012 9:20 pm
berg
Благодарю, Markiyan Hirnyk!
Просто и красиво.

Добавлено: Пн окт 15, 2012 10:46 am
Сергей46
Уважаемый berg, обычно я не помогаю студентам с решением примитивных примеров. Но тут вопрос несколько сложнее и поучительнее. Г-н Selin привел довольно эффективное решение для вашего примера при условии получения лишь кратных значений списка (его совет домыслить результата не возымел); именно это яаляется более естественной постановкой, чтобы не выводить кратные пары. Г-н Markiyan Hirnyk привел решение для более простого случая (не требовалось отделять “мух от котлет”). Однако, если в первом случае использовались разовые вызовы функций (по терминологии одного автора, правда, очень точно отражающей суть), то во втором использовалась загрузка всего пакета ListTools, что неэффективно, ибо Maple очень неэффективно (в отличие от Mathematica) оптимизирует память. Наконец, более эффективно использовать встроенные, а значит и более быстрые, и имеющиеся во всех версиях средства, в частности, функцию numboccur. Вот решение вашего примера в ее терминах:

> LS := (x::list) -> [op({seq([k, numboccur(x, k)], k=x)})]:
> L := [67, 19, 4, 90, 1, 5, 32, 90, 5, 5, 321]: LS(L);
[[321, 1], [32, 1], [5, 3], [1, 1], [90, 2], [4, 1], [19, 1],[67, 1]]
> L := [a, a+b, c, c, c, c, a+b0, d, d, a+b]: LS(L);
[[d, 2], [a + b0, 1], [c, 4], [a + b, 2], [a, 4]]

Дополнительно напомню, что индекстная перемення к в функциях типа seq носит локальный характер. Остальное “домыслите”. Предложенный прием имеет массу продолжений. Надеюсь, это сподвигнет вас на более глубокое освоение Maple. К сожалению, на большую детализацию времени нет, ждут подобные студенты.

Добавлено: Пн окт 15, 2012 2:57 pm
Markiyan Hirnyk
Сергей46 писал(а):Уважаемый berg, обычно я не помогаю студентам с решением примитивных примеров. Но тут вопрос несколько сложнее и поучительнее. Г-н Selin привел довольно эффективное решение для вашего примера при условии получения лишь кратных значений списка (его совет домыслить результата не возымел); именно это яаляется более естественной постановкой, чтобы не выводить кратные пары. Г-н Markiyan Hirnyk привел решение для более простого случая (не требовалось отделять “мух от котлет”). Однако, если в первом случае использовались разовые вызовы функций (по терминологии одного автора, правда, очень точно отражающей суть), то во втором использовалась загрузка всего пакета ListTools, что неэффективно, ибо Maple очень неэффективно (в отличие от Mathematica) оптимизирует память. Наконец, более эффективно использовать встроенные, а значит и более быстрые, и имеющиеся во всех версиях средства, в частности, функцию numboccur. Вот решение вашего примера в ее терминах:

> LS := (x::list) -> [op({seq([k, numboccur(x, k)], k=x)})]:
> L := [67, 19, 4, 90, 1, 5, 32, 90, 5, 5, 321]: LS(L);
[[321, 1], [32, 1], [5, 3], [1, 1], [90, 2], [4, 1], [19, 1],[67, 1]]
> L := [a, a+b, c, c, c, c, a+b0, d, d, a+b]: LS(L);
[[d, 2], [a + b0, 1], [c, 4], [a + b, 2], [a, 4]]

Дополнительно напомню, что индекстная перемення к в функциях типа seq носит локальный характер. Остальное “домыслите”. Предложенный прием имеет массу продолжений. Надеюсь, это сподвигнет вас на более глубокое освоение Maple. К сожалению, на большую детализацию времени нет, ждут подобные студенты.
Хорошая мысль, Ваш код примерно в 6 раз быстрее. Однако требованиям заказчика лучше соответствует sort(LS(L)) .

Добавлено: Пн окт 15, 2012 5:58 pm
berg
Уважаемый Сергей46!
Вы ошибочно отнесли меня к студентам. Мне уже за 70, и я слабо владею Мэплом. Поэтому "домысливать" у меня не получается. Но я благодарен Вам за предложенную процедуру и за то, что любезно откликнулись на мой вопрос.

Добавлено: Пн окт 15, 2012 7:54 pm
Сергей46
Уважаемый Berg, за “студента” не извиняюсь, ибо вы сами себя так обозвали. С остальным понятно. Рад, что в таком возрасте у вас такие серьезные интересы. Именно из уважения к вашкму возрасту решил еще раз ответить.

Уважаемый Markiyan Hirnyk! Я привел лишь основу, на базе которой можно получать решение целого ряда подобных задач (группировка элементов с одинаковыми кратностями и пр.). Это по той причине, что работая в области криптографии, я параллельно читаю курсы по алгебре и анализу для студентов. Матпакеты и программирование использую лишь как вспомогательные средства. Но мое кредо – не оказывать медвежью услугу студентам, которые в массе своей живут по принципу “сдал и забыл”. Поэтому и пытаюсь стимулировать их мысли не прямыми подсказками, а наводками. Что же до сортировки, то можно использовать нечто подобное (на примере имеющегося списка, можно привести и другие интересные варианты)

> L := [[321, 1], [32, 1], [5, 3], [1, 1], [90, 2], [4, 1], [19, 1], [67, 1]]:
> F := (x, y) -> evalb(z(x[1], y[1])): z := `<`: sort(L, F);
[[1, 1], [4, 1], [5, 3], [19, 1], [32, 1], [67, 1], [90, 2], [321, 1]]
> z := `>`: sort(L, F);
[[321, 1], [90, 2], [67, 1], [32, 1], [19, 1], [5, 3], [4, 1], [1, 1]]

Всегда надеешься, что наводка даст толчок к более серьезному изучению предмета. К сожалению, время не позволяет часто посещать форумы по интересам.

Играйте простую мелодию

Добавлено: Пн окт 15, 2012 8:10 pm
Markiyan Hirnyk
Сергей46 писал(а):Уважаемый Markiyan Hirnyk! Я привел лишь основу, на базе которой можно получать решение целого ряда подобных задач (группировка элементов с одинаковыми кратностями и пр.). Что же до сортировки, то можно использовать нечто подобное (на примере имеющегося списка, можно привести и другие интересные варианты)

> L := [[321, 1], [32, 1], [5, 3], [1, 1], [90, 2], [4, 1], [19, 1], [67, 1]]:
> F := (x, y) -> evalb(z(x[1], y[1])): z := `<`: sort(L, F);
[[1, 1], [4, 1], [5, 3], [19, 1], [32, 1], [67, 1], [90, 2], [321, 1]]
> z := `>`: sort(L, F);
[[321, 1], [90, 2], [67, 1], [32, 1], [19, 1], [5, 3], [4, 1], [1, 1]]

Пожалуйста, объясните, с какой целью Вы приводите "более интересные варианты"?

Добавлено: Пн окт 15, 2012 8:11 pm
berg
Можно ли произвести сортировку по второму элементу?
То есть получить следующий список:
[5,3],[90,2],[1,1],[4,1],[19,1],... и т.д.

Добавлено: Пн окт 15, 2012 8:42 pm
Сергей46
То Markiyan Hirnyk: А привел я лишь в порядке общей информированности. Если не интересно (будем надеяться), пропустите.

То Berg: Можно и по второму элементу (несложно усмотреть принцип)

> F := (x, y) -> evalb(z(x[2], y[2])): z:=`<`: sort(L, F);
[[67, 1], [19, 1], [4, 1], [1, 1], [32, 1], [321, 1], [90, 2], [5, 3]]