Консультация № 161458
26.02.2009, 11:29
0.00 руб.
0 6 1
Помогите, пожалуйста, с задачей!

Задачу нужно сделать с помощью указателей (создавать списки)и через процедуры. Также нужно использовать операторы case и ord.
Условие задачи
С клавиатуры вводится строка (тип string), в которой записан многочлен. Используя операторы case и ord нужно «распознать» многочлен, создать список и вывести многочлен на экран. Причем выведенный многочлен должен быть с упорядоченными степенями и коэффициентами
(пример)
Вводим
2x^3+4x^5+2+x^3
Выводим
4x^5 + 3x^3 + 2

Задачу нужно сделать с помощью указателей (создавать списки)и через процедуры.

Обсуждение

Неизвестный
26.02.2009, 22:24
общий
это ответ
Здравствуйте, Abelman!

Код программы в приложении.
Сначала вводятся данные и записываются в список (каждый следующий элемент записывается на первое место (так проще)), до тех пор пока не введём 0 0.
Потом перебирается список и ищется член с максимальной степенью. Далее список перебирается ещё раз и у всех членов с этой степенью суммируется коэффициент, далее всё это выводится на экран.
Успехов!

С уважением, Дмитрий.

Приложение:
program z161458;
const N = 100;{max кол-во вводимых пар}
type Tkoef = Real;{тип коэффициентов (целые или вещественные)}
TStep = Real;{тип степеней (целые или вещественные)}
T4len = record{член последовательности - }
koef : TKoef;{коэффициент перед ним}
step : TStep;{и его степень}
end;

ptr = ^element;
element = record
data : T4len;
next : ptr;
end;
var list : ptr;

{--------------------------------------------------------}
procedure Initialize;
begin
new(list);
list^.next := nil;
end;
procedure Die;
begin
Dispose(list);
end;
{--------------------------------------------------------}
procedure AddFirst(elem : ptr);{добавление элемента в начало списка}
begin
if list^.next = nil then
list^.next := elem
else
begin
elem^.next := list^.next;
list^.next := elem;
end;
end;

procedure vvod;{ввод данных}
var elem:ptr;
begin
repeat
new(elem);
Write('Введите коэффициент перед членом: ');
ReadLn(elem^.data.koef);
Write('Введите степень: ');
ReadLn(elem^.data.step);

elem^.next := nil;
AddFirst(elem);
Until (elem^.data.koef = 0)and(elem^.data.step = 0);
list^.next:=list^.next^.next;{Удаляем первый элемент т.к. он нулевой}
end;


Function FMax(var max:TStep):boolean;{поиск максимальной оставшейся степени с коэффициентом <> 0}
var nashli:boolean;
el:ptr;
i:Integer;
begin
nashli:=false;
el := list^.next;
i := 1;
while el <> nil do
begin
IF ((el^.data.step > max) or (not nashli)) and (el^.data.koef <> 0) then
begin
max:=el^.data.step;
nashli:=true;{в массиве ещё есть члены последовательности, с ненулевым коэффициентом}
end;
inc(i);
el := el^.next;
end;
FMax:=nashli;
end;

var
el:ptr;
kol,i:Integer;
max:TStep;
koef:TKoef;
StrKoef,StrStep:String[20];
begin
Initialize;
vvod;
While FMax(max) do{пока в списке есть члены с ненулевыми коэффициентами}
begin
koef:=0;
{считаем коэффициент перед членом с максимальной степенью в массиве}
el := list^.next;
i := 1;
while el <> nil do
begin
IF el^.data.step = max then{если это член с максимальной степенью - }
begin
koef:=koef + el^.data.koef;{считаем суммарный коэффициент перед ним}
el^.data.koef := 0;{зануляем коэффициент, чтобы больше не считать этот член}
end;
inc(i);
el := el^.next;
end;

Str(max:0:3,StrStep);{если степени - целые числа, то ":0:3" не нужно}
Str(koef:0:3,StrKoef);{если коэффициенты - целые числа, то ":0:3" не нужно}
IF Strkoef[1] <> '-' then
StrKoef:= '+' + StrKoef;
IF koef <> 0 then{выводим приведённый член последовательности}
IF max = 0 then
Write(StrKoef + ' ')
Else
IF max = 1 then
Write(StrKoef + 'x ')
Else
Write(StrKoef+'x^'+StrStep+' ');
end;
die;{очищаем память от списка}
ReadLn;
end.
Неизвестный
26.02.2009, 22:58
общий
Несколько исправлений к программе:
константа N (const N = 100;{max кол-во вводимых пар}) не нужна - можете стереть, и строку
" list^.next:=list^.next^.next;{Удаляем первый элемент т.к. он нулевой}" тоже лучше стереть, т.к. при этом первый элемент не удаляется, а просто "забывается" что он есть и при очистке памяти от списка, он остаётся и занимает память. На работоспособность программы эти изменения никак не повлияют.
Если что-то непонятно - пишите.
Неизвестный
27.02.2009, 20:17
общий
Большое Вам спасибо, но программа должна работать по другому. Должны быть использованны операторы case и ord.

Например, мы ввели строку 144x^4+7x+5. А дальше, используя оператор case мы "распознаём" введённую строку.
Неизвестный
27.02.2009, 21:03
общий
виноват, извиняюсь
перепутал вопрос с похожим, в котором надо было вводить многочлен так как я сделал..
Сейчас переделаю и напишу так как Вам необходимо.
Правда не очень представляю зачем и где тут использовать ord, но постараюсь сделать с ним.
Неизвестный
27.02.2009, 23:34
общий
Вот исправленная версия:
Код:
program z161458;
type Tkoef = Real;{тип коэффициентов (целые или вещественные)}
TStep = Real;{тип степеней (целые или вещественные)}
T4len = record{член последовательности - }
koef : TKoef;{коэффициент перед ним}
step : TStep;{и его степень}
end;

ptr = ^element;
element = record
data : T4len;
next : ptr;
end;
var list : ptr;

{--------------------------------------------------------}
procedure Initialize;
begin
new(list);
list^.next := nil;
end;
procedure Die;
var elem:ptr;
begin
elem:=list;
While list <> nil do
begin
list:=list^.next;
dispose(elem);
elem:=list;
end;
end;
{--------------------------------------------------------}
procedure AddFirst(elem : ptr);{добавление элемента в начало списка}
begin
if list^.next = nil then{если список пуст - }
list^.next := elem{прописываем добавляемый элемент в качестве первого}
else{иначе}
begin
elem^.next := list^.next;{назначаем "хвосту"(ссылке на следующий элемент) текущего элемента первый элемент списка}
list^.next := elem;{прописываем добавляемый элемент в качестве первого}
end;
end;

procedure Add4len(s:String);{разбор одного члена (строки вида "-23x^3")}
var elem:ptr;
koef,step:String;
code:Integer;
begin
new(elem);
IF pos('x',s) > 0 then{Если степень не нулевая}
begin
koef:=copy(s,1,pos('x',s)-1);{запоминаем коэффициент}
IF (koef = '+')or(koef = '-') then{если член вида "-x.." или "+x.." то коэффициент соответственно равен 1 или -1}
koef:=koef + '1';

IF pos('^',s) > 0 then{Если степень не равна 1}
step:=copy(s,pos('^',s)+1,255){запоминаем её}
Else
step:='1';
end
Else{если степень равна нулю}
begin
koef:=s;{то весь член - это коэффициент}
Step:='0';
end;
{добавляем член в список}
val(koef,elem^.data.koef,code);
val(step,elem^.data.step,code);
elem^.next := nil;
AddFirst(elem);
end;
procedure vvod;{ввод данных}
var s,s4len:string;
i:Integer;
isStepen:boolean;
znak:char;
begin
WriteLn('Введите многочлен: ');
ReadLn(s);
While pos(' ',s) > 0 do{удаляем пробелы из строки}
delete(s,pos(' ',s),1);
s4len:='';
isStepen:=false;
znak:='+';
For i:= 1 to length(s) do{перебираем строку}
case ord(s[i]) of{если символ: }
43,45:{+ или -}
IF isStepen then{если это знак степени (например, в строке "2x^-3" "-" перед "3")}
begin
s4len:= s4len + s[i];{просто дописываем знак к члену последовательности}
isStepen:=false;
end
Else{если это не знак степени - }
begin
Add4len(znak+s4len);{добавляем член в список}
s4len:='';
znak:=s[i];{запоминаем знак перед следующим членом}
end;
94: begin{^ - знак степени}
s4len:= s4len + s[i];
isStepen:=true;
end;
Else begin{иначе}
s4len:= s4len + s[i];{дописываем символ к члену}
isStepen:=false;{знак степени уже учли}
end;
end;
IF length(s4len) > 0 then{добавляем последний член}
Add4len(znak+s4len);
end;

Function FMax(var max:TStep):boolean;{поиск максимальной оставшейся степени с коэффициентом <> 0}
var nashli:boolean;
el:ptr;
i:Integer;
begin
nashli:=false;
el := list^.next;
i := 1;
while el <> nil do
begin
IF ((el^.data.step > max) or (not nashli)) and (el^.data.koef <> 0) then
begin
max:=el^.data.step;
nashli:=true;{в списке ещё есть члены последовательности, с ненулевым коэффициентом}
end;
inc(i);
el := el^.next;
end;
FMax:=nashli;
end;

var
el:ptr;
kol,i:Integer;
max:TStep;
koef:TKoef;
StrKoef,StrStep:String[20];
begin
Initialize;
vvod;
While FMax(max) do{пока в списке есть члены с ненулевыми коэффициентами}
begin
koef:=0;
{считаем коэффициент перед членом с максимальной степенью в списке}
el := list^.next;
i := 1;
while el <> nil do
begin
IF el^.data.step = max then{если это член с максимальной степенью - }
begin
koef:=koef + el^.data.koef;{считаем суммарный коэффициент перед ним}
el^.data.koef := 0;{зануляем коэффициент, чтобы больше не считать этот член}
end;
inc(i);
el := el^.next;
end;

Str(max:0:3,StrStep);{если степени - целые числа, то ":0:3" не нужно}
Str(koef:0:3,StrKoef);{если коэффициенты - целые числа, то ":0:3" не нужно}
IF Strkoef[1] <> '-' then
StrKoef:= '+' + StrKoef;
IF koef <> 0 then{выводим приведённый член последовательности}
IF max = 0 then
Write(StrKoef + ' ')
Else
IF max = 1 then
Write(StrKoef + 'x ')
Else
Write(StrKoef+'x^'+StrStep+' ');
end;
die;
ReadLn;
end.

Изменился только ввод многочлена и исправил недочёты, про которые писал выше.

Ещё раз извиняюсь за невнимательно прочтённое задание.
Неизвестный
28.02.2009, 19:07
общий
Большое вам спасибо!
Форма ответа