Консультация № 170430
14.07.2009, 16:29
0.00 руб.
0 18 1
Здрасте! Такой вот вопросик: сидел тут, сидел, разбирал понимаешь метод цифровой сортировки в паскале, вроде метод то понял, только вот не знаю как реализовать внесение данных по разрядам. Тобишь: когда разбираем много значений, раскладываем их по ячейкам 0..9 допустим, а ведь есть и повторяющиеся значения!
Так вот вопрос: как хранить в одной ячейке несколько значений, и после этого их оттуда достать?
Накодил тут немного, может подскажете что делать?
Только про мозги не надо, я и так знаю что не гений

Приложение:
Program lab1;
uses crt;
const
n=200; {Количество повторений}
var
x,i,j,quit,sel,pv,max,t,err,sp:integer;{переменные}
check,m,c,cc:real;
s,s2:string;
a: array[0..n] of integer;{массив}
b: array[0..n,0..n] of integer;{массив}
p: array[0..n] of integer;{массив}

procedure vivod(x:integer; g:array of integer); {процедура вывода содержимого массива (для переменых LC,CC)}
begin
pv:=pv+1; {номер строки}
if n<=200 then{выбор размерности}
if pv>9 then{если выведено более 9 строк}
begin
pv:=0;
writeln(g[x]:4);
end
else
write(g[x]:4)
else
if pv>19 then{если выведено более 19 строк}
begin
pv:=0;
writeln(g[x]:4);
end
else
write(g[x]:4);
end;


begin {начало программы}
clrscr; {очистка экрана}
randomize;
while quit<>1 do
begin
randomize;
clrscr;
writeln('-----------------------');
writeln('Laboratornaya rabota #3');
writeln(' 4ACTb 2');
writeln('1. Zapolnenie Serii');
writeln('2. Sortirovka');
writeln('3. Prosmotr massiva');
writeln('4. Exit');
writeln('-----------------------');
writeln('----BY-HELL_Phoenix----');
readln(sel);
case sel of
1:
begin {Пункт меню: Заполнение Серий}
clrscr;
writeln('-----------------------');
writeln('1. Slu4ayniy vibor');
writeln('2. Ot 1 do n');
writeln('3. Ot n do 1');
writeln('-----------------------');
writeln('----BY-HELL_Phoenix----');
readln(sel);
case sel of
1:
begin
clrscr;
{заполнение массива А случайными числами}
pv:=0; {обнуление количества строк}
check:=0; {обнуление контрольтной суммы}
writeln('Massiv A:');
a[1]:=random(5);
for i:=1 to n do
a[i+1]:=random(n+1);
for i:=1 to n do
vivod(i,a);
for i:=1 to n do
check:=check+a[i];
writeln(' Kontrolnaya summa = ',check:10:0);
writeln;
readln;
end;


2:
begin
clrscr;
pv:=0; {обнуление количества строк}
check:=0; {обнуление контрольтной суммы}
writeln('Massiv a:');
{заполнение массива}
for i:=1 to n do
begin
a[i]:=i;
vivod(i,a);
check:=check+a[i];{контрольная сумма}
end;
writeln(' Kontrolnaya summa = ',check:10:0);
readln;
end;
3:
begin
clrscr;
pv:=0; {обнуление количества строк}
check:=0; {обнуление контрольтной суммы}
writeln('Massiv a:');
j:=n;
{заполнение массива}
for i:=1 to n do
begin
a[i]:=j;
j:=j-1;
vivod(i,a);{вывод текущего элемента}
check:=check+a[i];{контрольная сумма}
end;
writeln(' Kontrolnaya summa = ',check:10:0);
readln;
end;

end;


end;
2:
begin
clrscr;
max:=a[1];
for i:=2 to n do
begin
if max<a[i] then
max:=a[i];
end;
str(max,s);
max:=length(s);
t:=max;
sp:=9;
for i:=1 to max do
begin
while sp<>0 do
begin
for j:=1 to n do
begin
str(a[j],s);
s2:=copy(s,t,t);
val(s2,x,err);
if x=sp then
b[x,j]:=a[j];
end;
sp:=sp-1;
end;
for i:=1 to max do
begin
while sp<>0 do
begin
for j:=1 to n do
begin
if b[sp,j]<>null then
a[j]:=b[sp,j];
end;
end;
end;
t:=t-1;
end;
readln;
end;
3:
begin
clrscr;
check:=0;
for i:=1 to n do
check:=check+a[i];
pv:=0;
writeln('Massiv A');
for i:=1 to n do
vivod(i,a);
writeln(' Kontrolnaya summa = ',check:10:0);
readln;
end;
4: break;
end;
end;





end.

Обсуждение

Неизвестный
14.07.2009, 16:30
общий
В общем мозги кипят... сам ничего умнее придумать не смог...
Неизвестный
14.07.2009, 17:32
общий
1) В любой программе, с подпрограммами особенно, плохо использовать глобальные переменные. Это источник труднообнаружимых ошибок.
2) Если "как хранить", то можно просто объявить двумерный массив, где второе число = число повторений.
3) В Вашей программе что-то много накручено - зачем? Попробуйте подробнее описать задачу, которую хотите выполнить. А то у Вас какие-то серии, о которых в исходном задании ничего не написано (?). Что такое LC, CC?
Если хотите, чтобы Вам помогли - помогите и нам
давно
Старший Модератор
31795
6196
14.07.2009, 21:18
общий
Hellphoenix:
Я бы Вам посоветовал посмотреть эту статью.
Идеи изложенные в ней позволят Вам максимально сократить код и упростить его.

Цитата: 237702
Так вот вопрос: как хранить в одной ячейке несколько значений, и после этого их оттуда достать?
Накодил тут немного, может подскажете что делать?


Вам это не нужно.
Т.к. у Вас числа генерируются случайно, а максимальное число трёх-значное, то я тоже, свою идею накодил(схематично):
Код:
k:=1;коэфициэнт проверяемой цифры
s:=1;индикатор выхода из цикла
repeatцикл сортировки
...очистка массива-списка В и цикл проверки всего списка А
x:=(a^.data div k) mod 10;получаем очередную цыфру
[color=green]тут переключение связей и расположение очередного элемента в нужное место, сильно не пинайте, т.к. писал без проверки

c:=a^.next;
a^.next:=b[x]^.next;
b[x]^.next:=a,
a:=c;
...окончание цикла
. . . тут формирование списка А из массива-списка В
k:= k * 10;следующий коэфициэнт
s:= ((s+k)div 10)+((s+k)mod 10);проверяем всели цифры проверили
until s=0;

После этого будет сформирован отсортированный список А.
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

Неизвестный
14.07.2009, 22:27
общий
Помните песню: тили тили, трали вали, так вот что означают
Код:
a^.next:=b[x]^.next;
?
давно
Старший Модератор
31795
6196
14.07.2009, 22:49
общий
Я эту песню помню.
Вы статью читали?
Это работа с указателями.
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

Неизвестный
15.07.2009, 18:48
общий
задание, исходный массив а отсортировать методом цифровой сортировки. Вот.. В Турбо паскале... Статью читал... еще до того как задать вопрос... а вопрос всетаки: какой тип переменных использовать для сортировки? Вот в той статье, интересующий меня элемент сравнивабт со шляпой..
Неизвестный
15.07.2009, 20:01
общий
Не элемент, а то, куда его кладут. И сортировка не цифровая, а поразрядная
А тот тип элементов нужно использовать, который нужно сортировать. Вы для каких хотите? Или просто так
Неизвестный
15.07.2009, 20:30
общий
нет ну вы как то не понимаете суть моих вопросов... выппажаясь текстом статьи, меня интересют не то что написано в листочках, а то чем является в данном случае шляпа! это массив? или что то другое? что это за тип данных?
давно
Старший Модератор
31795
6196
15.07.2009, 20:53
общий
Цитата: 237702
В Турбо паскале

В статье не используются объекты и классы и за исключением некоторых функций(delphi) всё остальное PASCAL, тем более, что описано результат работы функции.
Цитата: 237702
исходный массив а отсортировать методом цифровой сортировки.

Элементарно переделывается.
Цитата: 237702
какой тип переменных использовать для сортировки

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

теперь по вопросу:
Цитата: 237702
Тобишь: когда разбираем много значений, раскладываем их по ячейкам 0..9 допустим, а ведь есть и повторяющиеся значения!
Так вот вопрос: как хранить в одной ячейке несколько значений, и после этого их оттуда достать?

Цитата: Зенченко Константин Николаевич
Идеи изложенные в ней позволят Вам максимально сократить код и упростить его.

Как хранить и доставать было описано в статье.

К Вам встречный вопрос: Ответ выкладывать, для целого типа?
Меню нет, оформления нет, подпрограмм нет, но есть вывод-демонстрация работы этого метода.
Код:
const
n=13;{количество элементов}
m=1000;{число превышающее максимальное число разрядов}
var
a:array[1..n]of integer;{исходный массив}
b:array[0..9,1..n]of integer;{дополнительный массив}
k,l,i,j:integer;{служебные переменные}
begin
{создаем массив}
for i:=1 to n do
begin
a[i]:=random(m-1)+1;{создаем один элемент}
write(a[i]:6);{выводим его}
end;
writeln;
{коэфициэнт обрабатываемого разряда}
k:=1;
repeat
{сбрасываем дополнительный массив}
for i:=0 to 9 do
for j:=1 to n do
b[i,j]:=0;
{сортировка}
for i:=1 to n do
begin
j:=(a[i] div k)mod 10;{получаем цифру}
l:=1;{начинаем с первого элемента}
while b[j,l]<>0 do{ищем последний элемент}
inc(l);
b[j,l]:=a[i];{записываем его}
end;
{формируем исходный массив}
l:=1;
for i:=0 to 9 do
begin
j:=1;
while b[i,j]<>0 do
begin
a[l]:=b[i,j];{записываем текущий элемент}
write(a[l]:6);{выводим на экран, только для показа механизма сортировки}
inc(l);{увеличиваем счетчик в исходном массиве}
inc(j);{увеличиваем счетчик в дополнительном массиве}
end;
end;
writeln;
k:=k*10;{увеличиваем коэфициэнт обрабатываемого разряда}
until k=m;
readln;
end.
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

Неизвестный
15.07.2009, 21:14
общий
Обратите внимание на первых два рисунке в статье. Каждая колонка (разряд) и есть шляпа. Может быть реализована как массив (вот чем является шляпа) либо постоянный с запасом, либо динамический. В первом случае скорость работы выше, но может потребоваться для его размещения объем памяти, недоступный в Turbo Pascal. Во втором варианте память расходуется экономно, но скорость работы упадет в разы, так что при сортировке большого массива появятся проблемы.
Мои вопросы и были направлены на то, чтобы определить, сколько разрядов нужно Вам для сортировки
Неизвестный
16.07.2009, 17:27
общий
вот вы и ответили на мой вопрос, только вот n у меня не меньше 100, а я почему то пытался использовать массив nxn элементов, поэтому паскаль писал ошибку, уменьшить на 9xn не догадался
давно
Старший Модератор
31795
6196
16.07.2009, 18:01
общий
Hellphoenix:
было странно, если бы ТР7.0 не ругался, т.к. он не может создать переменную больше одного сегмента т.е. 65536 байт.
У Вас было 200х200х2(размер массива и размер одного элемента в массиве)=80000 байт.
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

Неизвестный
16.07.2009, 18:25
общий
ну, ваш код попрощеконечно пришлось немного подработать, но отлично работаетСпасибо!
Неизвестный
16.07.2009, 18:38
общий
Отсюда вывод: спрашивая, давайте как можно больше информации - так легче ответить как нужно.
ЗЫ: в Turbo Pascal (запуская Turbo.exe) не пробовал (скорее всего тоже пройдет), а вот, запуская BP.EXE - удавалось захватить памяти поболе.
Писал как-то даже выпуск рассылки на эту тему ООП - это просто? Часть 7. Блок памяти больше 64 К
давно
Старший Модератор
31795
6196
16.07.2009, 20:37
общий
Hellphoenix:
Теперь капельку "ругательств"
Цитата: 237702
вот вы и ответили на мой вопрос, только вот n у меня не меньше 100, а я почему то пытался использовать массив nxn элементов, поэтому паскаль писал ошибку, уменьшить на 9xn не догадался

нет ну вы как то не понимаете суть моих вопросов... выражаясь текстом статьи, меня интересют не то что написано в листочках, а то чем является в данном случае шляпа! это массив? или что то другое? что это за тип данных?

задание, исходный массив а отсортировать методом цифровой сортировки. Вот.. В Турбо паскале... Статью читал... еще до того как задать вопрос... а вопрос всетаки: какой тип переменных использовать для сортировки? Вот в той статье, интересующий меня элемент сравнивабт со шляпой.

Цитата: 237702
из вопроса раскладываем их по ячейкам 0..9 допустим

[offtop]сорри последовательность мини-форума нарушенга[/offtop]
Вы просто не внимательны, даже если Вы видели эту статью и Вам дают эту ссылку, ещё раз перечитайте её, но уже с ручкой и бумагой.
Вот момент на который нужно было обратить особое внимание (на таблицы, это и есть шляпа).
Цитата: из статьи
Впрочем, пора переходить к описанию метода. Проще всего его объяснить на примере. Допустим, нам надо отсортировать всего лишь набор из десятка двузначных чисел: (83, 26, 37, 43, 42, 51, 87, 13, 90, 45). Само название метода дает намек, как мы будем это делать, разумеется, поразрядно (здесь два десятичных разряда). Наиболее естественно сначала выписать все числа так, чтобы старшие разряды шли по возрастанию, а потом упорядочить внутри каждого разряда по второй цифре. Но если у вас полсотни таких чисел? Представьте себе, что они написаны на бумажках, и вы раскладываете их по корзинам (или шляпам, например). Понадобиться десяток корзин, в которые вы положите бумажки с самой левой цифрой, которая равна номеру корзины. А потом вам придется вынимать из каждой корзины ее содержимое и раскладывать по порядку на столе. На самом деле, начинать надо с младшей (правой) цифры. Возьмем десяток корзин, занумеруем их по порядку от 0 до 9 (настоящий программист считает именно с 0, а не с 1, именно поэтому у него постоянные проблемы с подсчетом в реальной жизни), и разложим в них числа, смотря только на правую цифру, это можно сделать, просмотрев числа по порядку всего одни раз:
тут первая таблица
Как видно, в некоторых ячейках таблицы совсем ничего нет, а кое-где есть несколько чисел, причем в том порядке, в каком они шли сначала (это важно!). Теперь выложим эти числа: (90, 51, 42, 83, 43, 13, 45, 26, 37, 87). Пока почти никакого намека на порядок. Но осталась еще одна цифра, и мы раскладываем числа именно по ней, причем опять в том порядке, в котором они идут:
тут вторая таблица
Посмотрим, что получилось: (13, 26, 37, 42, 43, 45, 51, 83, 87, 90). Вуаля! Все числа идут по возрастанию. Сортировка закончена. Самое главное здесь записывать числа в каждой ячейке именно по порядку просмотра массива, иначе фокус не получится!


Цитата: 237702
ваш код попроще

Это просто переработанная версия динамического варианта(см. статью) и подогнаная под Ваши условия(только массив).
Удачи Вам!
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

Неизвестный
16.07.2009, 20:49
общий
Зенченко Константин Николаевич:
Правильно, но если бы я сел перечитывать с ручкой, у меня еше бы пара дней ушла на это, а так, помогли разобраться где я ошибся, Спасибо еще раз!
давно
Старший Модератор
31795
6196
16.07.2009, 22:15
общий

Вы снова не внимательны.
Первый раз Вы не обратили внимание на примеры, а просто пошли смотреть код, поняли, что это не Ваше. Давая эту ссылку я говорил об идеях. Т.е. прочитав этот материал, Вам нужно было подругому посмотреть свою на задачу. Вы этого не эделали.
Как вам такое задание: найти факториал 2000? Очевидно, что это больше самого максимального целого типа.
Вам нужно только по другому посмотреть на саму задачу.
Овет можно найти в рассылке, но сперва попробуйте сами. А умножение бинарных чисел(х-разрядов), слабо?
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

давно
Старший Модератор
31795
6196
16.07.2009, 22:21
общий
это ответ
Здравствуйте, Hellphoenix.

В приложении код, который поможет Вам разобратся с возникшей проблемой.
Нужного визуального офрмления нет, только демонстрация работы метода. Остальное Вам нужно добавить самому.
Удачи!

Приложение:
const
n=13;{количество элементов}
m=1000;{число превышающее максимальное число разрядов}
var
a:array[1..n]of integer;{исходный массив}
b:array[0..9,1..n]of integer;{дополнительный массив}
k,l,i,j:integer;{служебные переменные}
begin
{создаем массив}
for i:=1 to n do
begin
a[i]:=random(m-1)+1;{создаем один элемент}
write(a[i]:6);{выводим его}
end;
writeln;
{коэфициэнт обрабатываемого разряда}
k:=1;
repeat
{сбрасываем дополнительный массив}
for i:=0 to 9 do
for j:=1 to n do
b[i,j]:=0;
{сортировка}
for i:=1 to n do
begin
j:=(a[i] div k)mod 10;{получаем цифру}
l:=1;{начинаем с первого элемента}
while b[j,l]<>0 do{ищем последний элемент}
inc(l);
b[j,l]:=a[i];{записываем его}
end;
{формируем исходный массив}
l:=1;
for i:=0 to 9 do
begin
j:=1;
while b[i,j]<>0 do
begin
a[l]:=b[i,j];{записываем текущий элемент}
write(a[l]:6);{выводим на экран, только для показа механизма сортировки}
inc(l);{увеличиваем счетчик в исходном массиве}
inc(j);{увеличиваем счетчик в дополнительном массиве}
end;
end;
writeln;
k:=k*10;{увеличиваем коэфициэнт обрабатываемого разряда}
until k=m;
readln;
end.
5
Об авторе:
Мне безразлично, что Вы думаете о обо мне, но я рад за Вас - Вы начали думать.

Форма ответа