#c #integer #double #type-conversion #16-bit
#c #целое #double #преобразование типа #16-разрядный
Вопрос:
У меня есть функция, которая принимает 16-битное целое число без знака и преобразует его в double . Данные поступают от датчика температуры (MCP9808), и функция преобразует их в градусы Цельсия.
Функция определяется следующим образом:
double convert_tempc(uint16_t data) {
double temp = data amp; 0x0FFF;
temp /= 16.0;
if (data amp; 0x1000) temp -= 256;
return temp;
}
Мой вопрос в том, как я могу выполнить обратное этой серии операций?
Мне нужна функция для нахождения 16-битного значения, создаваемого этим датчиком, которое приводит к заданной температуре в градусах Цельсия.
Поскольку 16-разрядное значение может представлять только конечное число значений, я полагаю, что обратной функции потребуется найти ближайший double, который может быть представлен, а затем выполнить обратное преобразование.
Есть ли какой-нибудь простой способ сделать это?
Функция написана на C, но я буду реализовывать ее на Python.
Комментарии:
1. «Функция написана на C, но я буду реализовывать ее на Python». Что ж, удачи, тогда сделайте это и спросите еще раз, если у вас возникли конкретные проблемы с этим. 16-разрядное целое число по-прежнему является целым числом, только с ограниченным максимальным значением. В чем ваш вопрос?
2. Я не спрашиваю о преобразовании функции в python, я спрашиваю о нахождении серии операций, которые выполняли бы функциональную инверсию (возьмите double, выплюните uint16_t). Я не беспокоюсь о преобразовании c в python.
3. Вы имеете в виду изменение операторов?
-=
соответствует=
,/=
соответствует*=
; побитовые операции просто проверяют диапазоны, но с потерями, поэтому вы все равно не можете быть точными. В основном просто применяйте операторы наоборот.int(temp * 16) amp; 0xFFFF
должно сделать.4. Строго говоря, эта функция не обратима, потому что она теряет 3 самых значимых бита
data
. Однако, если вас не волнуют эти биты, или датчик возвращает данные только в диапазоне0 <= data <= 0x1fff
, тогда инвертировать функцию просто.5. @MisterMiyagi: это неправильно обрабатывает знаковый бит. Но
int(temp * 16) amp; 0x1FFF
выглядит довольно неплохо. 🙂
Ответ №1:
Вот некоторый код, который проверяет формулу, предложенную в комментариях.
def u16_to_float(data):
temp = data amp; 0x0FFF
temp /= 16.0
if data amp; 0x1000:
temp -= 256
return temp
def float_to_u16(temp):
return int(temp * 16) amp; 0x1FFF
# test
for data in range(0x2000):
temp = u16_to_float(data)
u = float_to_u16(temp)
assert u == data, (data, temp, u)
print('Ok')