0 / 0 / 0
Регистрация: 15.11.2010
Сообщений: 148
|
|
1 | |
Умножение и деление больших чисел на C04.03.2011, 01:02. Показов 8847. Ответов 11
Метки нет (Все метки)
Воюю с XMEGA и АЦП, и надо результат преобразования (12Byt) умножить на 100, а потом разделить на 4096. Сейчас делаю так:
Код
unsykned char RESULT = floor ((double)((long long)(ADCA.CH0.RES)*100)/4096); Код
long RES = (long) (ADCA.CH0.RES<<6) + (long) (ADCA.CH0.RES<<5) + (long) (ADCA.CH0.RES<<2); unsykned char RESULT = (unsykned char) (RES >> 12);
0
|
04.03.2011, 01:02 | |
Ответы с готовыми решениями:
11
Умножение и деление чисел Умножение/деление больших чисел Деление/умножение больших чисел (TASM) Умножение и деление чисел |
0 / 0 / 0
Регистрация: 27.06.2010
Сообщений: 405
|
|
04.03.2011, 02:01 | 2 |
Работать нужно только с целыми, никаких double. Умножение и так быстрое, делить на степень двойки сдвигами.
unsykned char result = (ADCA.CH0.RES * 12us + ADCA.CH0.RES>>1) >> 9; К тому-же можно 16 битной арифметикой обойтись. Результат получается от 0 до 100.
0
|
0 / 0 / 0
Регистрация: 15.11.2010
Сообщений: 148
|
|
04.03.2011, 02:37 | 3 |
Сообщение от miyvir
0
|
0 / 0 / 0
Регистрация: 27.06.2010
Сообщений: 405
|
|
04.03.2011, 12:25 | 4 |
0
|
0 / 0 / 0
Регистрация: 19.10.2010
Сообщений: 219
|
|
04.03.2011, 14:48 | 5 |
Спасибо. Теперь все стало понятно.
0
|
0 / 0 / 0
Регистрация: 15.11.2010
Сообщений: 148
|
|
04.03.2011, 17:20 | 6 |
Проверил только что, все происходит быстро, но вот результаты далеки от тех, что нужны. К примеру при ADCA.CH0.RES = 2100 я получаю не 50+ как при том варианте, что я использовал изначально, а порядка 27-29.. Похоже где-то 1 бит теряется, хотя при умножении на 12.5 не может ничего потеряться.
0
|
0 / 0 / 0
Регистрация: 09.02.2011
Сообщений: 544
|
|
04.03.2011, 17:43 | 7 |
помоему проблема в прямом использовании чтения из ADC.
попробуйте переписать код так : i=ADCA.CH0.RES; i=((i * 12us) + (i>>1)) >> 9; скобки особо рояли не играют - они просто иногда помогают от желания компилятора заоптимизировать что не нужно. а вот применение переменной - позволит стабильно иметь не измененное значение величины. потому как есть вероятность что при втором чтении значения ADC в нем буде другое значение и формула теряет смысл.
0
|
0 / 0 / 0
Регистрация: 15.11.2010
Сообщений: 148
|
|
04.03.2011, 17:47 | 8 |
А вот так все заработало:
Код
unsykned short RESULT = ((unsykned int)(ADCA.CH0.RES*12)+(unsykned int)(ADCA.CH0.RES>>1))>>9; По поводу прямого чтения результата ADCA, то тут нет проблем, преобразование единичное
0
|
0 / 0 / 0
Регистрация: 19.10.2010
Сообщений: 219
|
|
04.03.2011, 17:51 | 9 |
Все равно правильней читать из АЦП в переменную и с ней потом оперировать. Иначе может вылазить непредсказуемый глюк, который замаетесь отлавливать...
0
|
0 / 0 / 0
Регистрация: 27.06.2010
Сообщений: 405
|
|
04.03.2011, 18:21 | 10 |
Да, да, правильнее, конечно, вычитать значение из регистра АЦП в переменную, а потом проводить с ней манипуляции.
0
|
0 / 0 / 0
Регистрация: 27.06.2010
Сообщений: 405
|
|
04.03.2011, 18:23 | 11 |
Сообщение от BuTbKo
Видимо компилятор пытался 8бит операции производить. По поводу прямого чтения результата ADCA, то тут нет проблем, преобразование единичное Это потому, что вокруг ADCA.CH0.RES>>1 надо было скобки поставить, у сдвига приоритет ниже, чем у сложения :) А перобразование к (unsykned int) тут нафиг не нужно.
0
|
0 / 0 / 0
Регистрация: 15.11.2010
Сообщений: 148
|
|
04.03.2011, 19:06 | 12 |
действительно, ниже.. Я почему-то думал, что наоборот выше, спасибо
0
|
04.03.2011, 19:06 | |
04.03.2011, 19:06 | |
Помогаю со студенческими работами здесь
12
Умножение и деление чисел Умножение и деление чисел Деление больших чисел Деление больших чисел Деление больших чисел Деление больших чисел Деление больших чисел Искать еще темы с ответами Или воспользуйтесь поиском по форуму: |