Код является предстандартным C, поэтому он не использует прототипы (но объявляет функции, хотя, по-видимому, нет, если в этом нет крайней необходимости).В определениях функций используется предварительно стандартный стиль K & R для объявления параметров функции.С непрототипированными функциями на программиста возлагается обязанность гарантировать, что функции вызываются с правильным набором аргументов, и что если функция ничего не возвращает, то ничего не делается с ее «значением».
Если из функции возвращается что-то отличное от int
, функция должна быть объявлена (что не обязательно является прототипом), чтобы компилятор знал тип данных, возвращаемых из функции.Без объявления компилятор будет считать, что возвращается int
(но если функция ничего не возвращает, это нормально, если вы ничего не пытаетесь сделать с функцией 'result').
Вот несколько прямых комментариев к вашим вопросам:
/* prototypes? ( shouldn't they be outside the main ) */
// this declares that function `rnd()` returns a double. Technically, it's
// not a prototype. Without the declaration the compiler would assume that it
// returns an `int` so trying to use it wouldn't work. It could be declared
// outside `main()`, but it's OK to have it declared within the scope of
// `main()`, just like it would be for a prototype. That just means that
// outside of `main()` the declaration is no longer in effect, so any calls
// to `rnd()` would assume that `int` is returned (incorrectly).
double rnd(), sd;
/* type cast, why?? */
// the cast is unnecessary and redundant, but OK
sd = (double)(ne);
/* no idea what initrnd does */
// apparently `initrnd()` initializes the rng seed (see below). There's
// no declaration in sight, so the compiler will default the return type
// to `int` (unless it's in `stdio.h`).
initrnd(sd/(sd+187.9753));
/* writes the buffer, how does it know the file name? */
// `1` is the file descriptor for `stdout`. Today this would probably
// be specified using `STDOUT_FILENO`, but even today `STDOUT_FILENO` is
// required to be 1 (by POSIX).
write(1, buf, ne*sf);
}
initrnd(sd)
/* again no idea, why isn't this function void */
// `void` didn't exist pre-ANSI standard.
// so this function 'returns' `int` by default.
double sd;
{
seed = sd;
return(0);
}