Я разрабатываю приложение, которое использует NI-DAQ, и ниже приведены некоторые методы, которые были предоставлены поставщиком.
void someMethod(Calibration *cal, float myArray[], float result[])
{
newMethod(&cal->rt,myArray,result,cal->cfg.TempCompEnabled);
}
void newMethod(RTCoefs *coefs, double myArray[],float result[],BOOL tempcomp)
{
float newMyArray[6];
unsigned short i;
for (i=0; i < 6; i++)
{
newMyArray[i]=myArray[i];
}
}
Я в основном вызываю someMethod (), предоставляя массив с шестью элементами ([6]) для myArray [] и result []. Как вы можете видеть в коде, впоследствии вызывается newMethod (), и float myArray [6] передается в двойной аргумент myArray [] (я действительно не понимаю, почему разработчик этого кода решил использовать двойной массив, поскольку единственный массив, объявленный внутри newMethod (), является типом с плавающей запятой).
Теперь возникает моя проблема: внутри цикла for некоторые значения передаются без проблем, но когда четвертое и пятое значения передаются в newMyArray [], он получает «-1. # INF0000» для обоих значений. На первый взгляд, я думал, что это будет какое-то мусорное значение, но «-1. # INF0000» присутствует при каждом выполнении.
Я знаю, что язык C иногда бывает сложным, но я действительно не знаю, почему это происходит …
Второй параметр для newMethod
имеет тип double *
, Но вы передаете ему значение типа float *
,
В C ++ или в C, если был прототип newMethod
в области видимости это должно привести к ошибке компиляции. Не существует неявного преобразования между типами указателей, за исключением void *
,
Однако в C, если в области видимости нет прототипа, вы можете не получать предупреждения; просто неопределенное поведение во время выполнения, потому что функция была вызвана с аргументами другого типа (после продвижения аргументов по умолчанию) к тому, с которым она была определена.
Если есть объявление не прототипа newMethod
по объему вы не получите предупреждения; если не было никакого объявления вообще, то в C89 код является законным (то есть предупреждение является необязательным), но в C99 он должен предупредить, что newMethod
был вызван без объявления.
(Поэтому важно, будет ли это программа на C или C ++).
Если вы находитесь в C и не получаете предупреждения, добавьте прототип перед всем этим:
void newMethod(RTCoefs *coefs, double myArray[],float result[],BOOL tempcomp) ;
Тогда вы получите ошибку компилятора.
Проблема заключается в типах и в том, что массивы распадаются на указатели при передаче в функции. Поэтому, когда вы передаете указатель на float
массив для someMethod
он, в свою очередь, передает его как указатель на массив double
в newMethod
, И как вы (должны) знать размер float
и размер double
не то же самое, поэтому в newMethod
код читает данные за пределами начального (float
) массив, который вы передали, что приводит к неопределенное поведение.
Компилятор должен был предупредить вас об этом.
-1.#INF0000
Я полагаю, что MSC представляет
отрицательная бесконечность. Что вы получаете от двойного до
преобразование с плавающей запятой, когда значение double слишком велико
представлены в поплавке.