Перейти к содержанию
    

Как реализовать генератор квадратуры

Всем привет!

Вот есть задача - генерировать квадратурный сигнал для DDC. DDC сам реализован внутри DSP, поэтому надо алгоритм чтобы его можно было-бы реализвать потом на аасемблере.

Используется плавующая точка.

В идеальном случае ф-я должна выглядеть так:

result = GenSinCos(float freq); где result это структура содержащая Cos и Sin, т.е. сигналы сдвинуты на 90 градусов.

freq - 0...1.

Ф-я вызывается для каждого отсчета. Начальная фаза в общем не очень важна. Главное чтобы 90 градусов было. По идее это даже не ф-я а макрос.

Как-то так.

Может кто уже встречал подобное? Или может уже есть готовые решения?

 

Особенность в том, что наверняка есть решение которое не вызывает ф-ю sin и cos каждый раз. :)

 

Спасибо!

 

PS. Табличный метод не предлагать! :)

 

Изменено пользователем Russky

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Особенность в том, что наверняка есть решение которое не вызывает ф-ю sin и cos каждый раз. :)

....

PS. Табличный метод не предлагать! :)

..не понял я что-то, вы считать не хотите и в таблицу смотреть, тогда как же?

з.ы.

другое дело что синус посчитать по разному можно, но считать надо таки.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Особенность в том, что наверняка есть решение которое не вызывает ф-ю sin и cos каждый раз. :)

sin = sqrt(1 - cos^2) ?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Это прекрасно!! хороший синус. будет всегда не меньше 1. а иногда и побольше.

 

sin = sqrt(1 + cos^2) ?

 

Что касается начальной задачи, то решение есть!!! явочным порядком можно вызывть синус и косинус например каждый 10-й раз.. или даже 100-й. можно вообще ни разу не вызывать. всё зависит ведь от необходимой точности описания функций

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Это прекрасно!! хороший синус. будет всегда не меньше 1. а иногда и побольше.

Это точно! Вот хороший синус: sin(pi/2 - 2.06345i) = 4.0001. :biggrin:

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Это прекрасно!! хороший синус. будет всегда не меньше 1. а иногда и побольше.

большое спасибо за правку, торопился и ошибся

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Ну, конечно, CORDIC. Какие могут быть сомнения?!

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

На вычислительных платформах, на которых цена уножения равна цене сложения, а это любые dsp, смысла в кордике нет.

 

Ну, конечно, CORDIC. Какие могут быть сомнения?!

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Поясню. Есть методы генерирования синусоидально сигнала на основе биквада. Т.е. там просто рекурсивно вычисляется каждое следуюшее значение. Генератор в чистом виде.

Там меняя коэффициенты биквада, можно менять частоту. Там фаза не важна, важна только частота.

Я думаю, что должны быть методы, которые позволяют генерировать синус и косинус вместе, подобным образом. Дополнительным условием для данной ф-и есть разница фаз в 90 градусов.

Т.е либо начальные условия для генератора задавать, либо еще что-то. Но в общем это должно быть рекурсивное вычисление, где каждый следующий отсчет зависит от предыдущих. Это не синус и косинус в чистом виде. Нужен именно генератор (так как он более экономичен к вычислениям).

 

 

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Но в общем это должно быть рекурсивное вычисление, где каждый следующий отсчет зависит от предыдущих. Это не синус и косинус в чистом виде.

 

Нужен именно генератор (так как он более экономичен к вычислениям).

Школьная тригонометрия рулит.. :rolleyes:

 

sin[2*pi*f*(t+Δt)] = sin[2*pi*f*t] * cos[2*pi*f*Δt] + cos[2*pi*f*t] * sin[2*pi*f*Δt];

cos[2*pi*f*(t+Δt)] = cos[2*pi*f*t] * cos[2*pi*f*Δt] - sin[2*pi*f*t] * sin[2*pi*f*Δt];

 

Полагая, что t+Δt == (n+1)*Δt, находим формулы рекурсии:

 

sinn+1 == sin[2*pi*f*(n+1)*Δt] = sin[2*pi*f*n*Δt] * cos[2*pi*f*Δt] + cos[2*pi*f*n*Δt] * sin[2*pi*f*Δt] == sinn * cos[2*pi*f*Δt] + cosn * sin[2*pi*f*Δt];

cosn+1 == cos[2*pi*f*(n+1)*Δt] = cos[2*pi*f*n*Δt] * cos[2*pi*f*Δt] - sin[2*pi*f*n*Δt] * sin[2*pi*f*Δt] == cosn * cos[2*pi*f*Δt] - sinn * sin[2*pi*f*Δt];

 

Понятно, что sin[2*pi*f*Δt] и cos[2*pi*f*Δt] это константы, зависящие от f и Δt и выбираются так, чтобы 1/(f*Δt) = 2N == nmax+1.

 

Начальные значения:

 

sin0 = 0;

cos0 = 1;

 

Значения после переполнения счетчика n = (nmax+1)%2N == 0, полагаем равными:

 

sin2N = 0;

cos2N = 1;

 

Это предотвратит накопление ошибок..

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Что касается начальной задачи, то решение есть!!! явочным порядком можно вызывть синус и косинус например каждый 10-й раз.. или даже 100-й. можно вообще ни разу не вызывать. всё зависит ведь от необходимой точности описания функций

 

Соглашусь FatRobot, выбор алгоритма должен определяться тем, сколько надо SFDR и сколько mips можно потратить. Отбрасывать что-то с порога глупо.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Школьная тригонометрия рулит.. :rolleyes:

...

Это предотвратит накопление ошибок..

Спасибо. Надо попробовать.

Как попробую - напишу.

Пока все выглядет очень даже ничего! :)

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

На вычислительных платформах, на которых цена уножения равна цене сложения, а это любые dsp, смысла в кордике нет.

Насчет любых DSP не согласен. Недавно решали задачу, в которой нужно вычислять много арктангенсов, DSP TigerSHARC 101, CORDIC + SIMD дал результат лучше (в смысле вычислительных затрат) чем оптимизированный полиномиальный, хотя отдельно взятый CORDIC проигрывает.

 

ТС: хочу обратить Ваше внимание, что в DDC с целью подавления спуров при генерации квадратурной гармоники используются некоторые хитрости, например, младшие разряды заменяются на соответствующий отрезок ПСП. Если не ошибаюсь, в Матлабе есть такая модель (или у Xilinx-а в генераторе корок, запамятовал уже).

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Тут всё на веру, конечно. Не ставя под сомнение квалификацию. Но вот здесь http://www.opensource.apple.com/source/Lib...ce/Intel/atan.c

за где-то 15 умножений и 15 сложений получается точность double на входе и выходе для atan.

 

Насчет любых DSP не согласен. Недавно решали задачу, в которой нужно вычислять много арктангенсов, DSP TigerSHARC 101, CORDIC + SIMD дал результат лучше (в смысле вычислительных затрат) чем оптимизированный полиномиальный, хотя отдельно взятый CORDIC проигрывает.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...