Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Центр помощи > [Pascal] Задачи с функциями и процедурами


Автор: STRIKER221 3.11.2006, 16:11
Z=(sign(X)+sign(Y))expX    sign(x+y)         (expX=Степень Х)
Замечание: sign - фунция, возвращающая знак своего аргумента (например) sign (-6)=-1 
Функция sign определяется так: 
Sign(a)=:
-1 при а<0;
0 при а=0;
1 при а>0.

Исходные данные:                       Результат:
1. X=5    Y=-5                                Z=0
2. X=-7   Y=0                                 Z=1

Автор: Kuvaldis 3.11.2006, 23:17
STRIKER221, 
Цитата

Z=(sign(X)+sign(Y))expX    sign(x+y)         (expX=Степень Х)

я не совсем понял, как здесь используется expX
Ты ничего не пропустил в описании функции?

Автор: STRIKER221 3.11.2006, 23:32
expX это степень в которую возводится (sign(X)+sign(Y))

Автор: STRIKER221 6.11.2006, 13:02
там за место sign* подставляется значение -1 ,0 или 1. Складываются, возводятся в степень и потом перемножаются.

Автор: Kuvaldis 6.11.2006, 18:29
STRIKER221, 
Код

//------------------------------------------------------------------
function Sign(x : integer) : integer;
begin
    if (x < 0) then
       Sign := -1
    else if (x = 0) then
       Sign := 0
    else
       Sign := 1;
end;
//------------------------------------------------------------------
function degree(x, deg : integer) : real;
var
    i : integer;
    sign : integer;
    res : real;
begin
    if (deg < 0) then
    begin
        sign := -1;
        deg := -deg;
    end
    else
        sign := 1;

    res := 1;
    for i := 1 to deg do
        res := res * x;

    if (sign = -1) then
       res := 1 / res;

    degree := res;
end;
//------------------------------------------------------------------
var
  x, y : integer;
  res : real;
begin
  Write('x = ');
  Readln(x);
  Write('y = ');
  Readln(y);
  res := degree(Sign(x) + Sign(y), x)  * Sign(x + y);
  writeln('Result = ', res : 0 : 2); 
  readln; 
end.
//------------------------------------------------------------------

Автор: STRIKER221 6.11.2006, 20:36
Код

  if (sign = -1) then
       res := 1 / res;

А что делает эта часть????

Автор: Kuvaldis 7.11.2006, 00:04
STRIKER221, 
Цитата

А что делает эта часть????

если степень числа - отрицательная, то по определению
a ^ (-x) = 1 / a^x
Мы в данной задаче не можем пользоваться стандартными функциями типа exp(), ln() так как основания у нас могут быть и отрицательные, что для данных функций противопоказано

Автор: STRIKER221 7.11.2006, 03:04

Спасибо

Автор: STRIKER221 7.11.2006, 14:49
Какой командой добавить условие: когда сумма равна 0 выводить : Деление на 0 невозможно?
Код

begin
if (deg < 0) then
begin
  sign := -1;
  deg := -deg;
end
  else
 sign := 1;
 res := 1;
 for i := 1 to deg do
 res := res * x;
if (sign = -1) then
 res := 1 / res;
 degree:= res;
end;

Это будет что-то типа:
Код

if (sign =  0) then
writeln('...')
 ?
Но надо не if а что?

Автор: Kuvaldis 7.11.2006, 15:43
STRIKER221, 
Код

//------------------------------------------------------------------
function Sign(x : integer) : integer;
begin
    if (x < 0) then
       Sign := -1
    else if (x = 0) then
       Sign := 0
    else
       Sign := 1;
end;
//------------------------------------------------------------------
// return false, if error
function degree(x, deg : integer; var res : real) : boolean;
var
    i : integer;
    sign : integer;
begin
    if (deg = 0) then
    begin
        res := 1;   // default
        degree := true;
        Exit;
    end;

    if (deg < 0) then
    begin
        sign := -1;
        deg := -deg;
    end
    else
        sign := 1;

    res := 1;
    for i := 1 to deg do
        res := res * x;

    if (sign = -1) then
    begin
        if (res = 0) then
        begin            
            degree := false;
            Exit;
        end                
            res := 1 / res;                     
     end;
    
     degree := true;      
end;
//------------------------------------------------------------------
var
  x, y : integer;
  res : real;
begin
  Write('x = ');
  Readln(x);
  Write('y = ');
  Readln(y);
  if ( degree(Sign(x) + Sign(y), x, res) = false ) then
     writeln('Error! Zero dividing!')
  else
  begin
      res := res  * Sign(x + y);
      writeln('Result = ', res : 0 : 2);
  end;

  readln; 
end.
//------------------------------------------------------------------

Автор: volvo877 8.11.2006, 01:39
Kuvaldis,  smile 
Ты чего это?

Код

    if (sign = -1) then
    begin
        if (res = 0) then { <--- Чему равно res ? }
        begin
            res := 0;  { <--- ??? Зачем лишнее делать ??? }
            degree := false;
        end
        else
        begin
            res := 1 / res;
            degree := true;
        end;    
    end;


Вот такая реализация не будет проще читаться?
Код
function degree(x, deg : integer; var res : real) : boolean;
var
    i : integer;
    sign : integer;
begin
    degree := true;
    if (deg = 0) then
    begin
        res := 1;   // default
        Exit;
    end;

    if (deg < 0) then
    begin
        sign := -1;
        deg := -deg;
    end
    else
        sign := 1;

    res := 1;
    for i := 1 to deg do
        res := res * x;

    if (sign = -1) then
    begin
        if (res = 0) then degree := false
        else res := 1 / res;
    end;
end;
Кстати, в твоей реализации, что вернется, если изначально deg > 0? Я тебе скажу: False - это значение по умолчанию, ты же нигде в таким случае результат в True не перебрасываешь... А должно вернуться именно True, ведь ошибки не было, не так ли?

А Sign я бы вообще вот так написал:
//------------------------------------------------------------------
Код
function Sign(x : integer) : integer;
begin
    if (x = 0) then Sign := 0
    else Sign := X div Abs(X);
end;

Автор: Kuvaldis 8.11.2006, 02:38
volvo877, 
Цитата

Вот такая реализация не будет проще читаться?

У меня привычка код оформлять от С++ (основной язык для меня)

Цитата

Кстати, в твоей реализации, что вернется, если изначально deg > 0? Я тебе скажу: False - это значение по умолчанию, ты же нигде в таким случае результат в True не перебрасываешь... А должно вернуться именно True, ведь ошибки не было, не так ли?

да... на самом деле проглядел. Спасибо. Не зря ведь говорят: посмешишь - людей насмешишь (задачка-то легкая smile идею показал, а протестить до конца было лень.

P.S. Я тебе удивляюь и снимаю шляпу. Хоть и появляешься ты не часто, но всегда ОЧЕНЬ дельные советы даешь. В данном случае красивая реализация функции Sign() 
Так что думаю, что + ты заслужил smile 

Автор: Мист 26.12.2008, 21:39
[Pascal]Задачи с фунцыями и процедурами;(школьные задачи)
Решите плизз)))
№1 Найти все  простые числа которые меньше 100
№2 Найти разложение на разложение на  множители всех натуральных чисел з отрезка[a;b]

Автор: 2p0i 27.12.2008, 00:28
Писал прямо в броузере, лень проверять smile
Цитата
№1 Найти все  простые числа которые меньше 100

Код

var i, j : integer; ok: boolean;
begin
  for i := 2 to 100 do begin
    ok := true;
    for j := 2 to i/2 do 
      if (i mod j <> 0)
        ok := false;
    if ok then write(i, ' ');
  end;
  writeln;
  readln;
end.

Цитата
№2 Найти разложение на разложение на  множители всех натуральных чисел з отрезка[a;b]

Код

var a, b, i, j, t: integer;
begin
  readln(a, b);
  for i := a to b do begin
    write(i, ':');
    t := i;
    for j := 2 to i/2 do begin
      while t mod j = 0 do begin
        write(' ', j);
        t := t div j;
      end;
    end;
    writeln;
  end;
end.


Автор: volvo877 27.12.2008, 00:57
Цитата(2p0i @  26.12.2008,  23:28 Найти цитируемый пост)
лень проверять
В следующий раз лучше проверь... Во-первых, не 
Цитата
Код
      if (i mod j <> 0)
        ok := false;

, а 
Код

      if (i mod j = 0) then ok := false;
(разница - критическая). Во вторых, деление с циклом For несовместимо, будет ошибка, надо брать целую часть Trunc-ом. Ну, и в третьих - если хочется ускорить программу в 4 раза (525 проверок против твоих 2401):
Код
var i, j: integer; ok: boolean;
begin
  for i := 2 to 100 do begin
    ok := true;
    for j := 2 to trunc(sqrt(i)) do { <-- До корня из i проверять достаточно }
      if (i mod j = 0) then ok := false;

    if ok then write(i, ' ');
  end;
  writeln;
  readln;
end.

Автор: Мист 27.12.2008, 08:56
Спосибо)))ток щас догоню как это с функцией сделать

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)