スマートフォンが LTE や 5G で高速通信できるのはなぜでしょうか。Wi-Fi ルータが同じ周波数帯で大量のデータを運べるのはどうしてでしょうか。その答えの核心にあるのが「IQ直交変調(quadrature modulation)」です。ひとつの搬送波(キャリア)の上に、振幅情報だけでなく位相情報まで載せることで、限られた電波の帯域を文字通り「使い切る」ための基盤技術です。
少し意外なことに、同じ周波数の搬送波でありながら、まったく独立した2つの情報の流れ(チャネル)を1本の電波に重ねて送り、受信側で完全に分離して取り出すことができます。これは魔法のように聞こえますが、その秘密は $\cos$ と $\sin$ という2つの波が持つ「直交性」という数学的な性質にあります。本記事では、この直交性がどのように2チャネルの分離を可能にするのかを、数式の一行一行を省略せずに導出し、Python で実際に変調・復調を行って確かめます。
IQ直交変調を理解すると、次のような分野への見通しが一気に開けます。
- ディジタル変調(QAM/PSK): QPSK、16QAM、64QAM といったあらゆるディジタル変調方式は、IQ平面上のどこに信号点を置くかという問題に還元されます。IQ変調はその「土台」です
- ソフトウェア無線(SDR): 現代の無線機は、アナログ部で信号を I と Q の2つのベースバンド信号に落とし込み、あとはすべてディジタル信号処理で扱います。IQ表現は SDR の共通言語です
- レーダー・計測: ドップラー速度の符号(近づくか遠ざかるか)を判別するには I と Q の両方が必要です。複素信号の位相回転の向きが速度の符号を担います
- アンテナ・ビームフォーミング: 各素子に与える複素ウェイトは、まさに I と Q(振幅と位相)の組み合わせです
本記事の内容
- 同相(I)・直交(Q)成分という考え方の直感
- 実信号 $s(t) = I\cos\omega t – Q\sin\omega t$ の構成と意味
- $\cos$ と $\sin$ の直交性、乗算+ローパスフィルタによる I/Q 分離の導出(省略なし)
- 複素包絡線 $g(t) = I + jQ$ と $s(t) = \mathrm{Re}\{g(t)e^{j\omega t}\}$ の関係
- IQ変調器・IQ復調器の回路構成と数式
- QAM/PSK が IQ平面上の点配置に他ならないこと
- ヒルベルト変換・解析信号との接点
- IQ不平衡(ゲイン誤差・位相誤差)が生む像信号とコンスタレーション歪み
- Python による変調・復調・コンスタレーション・IQ不平衡の可視化
前提知識
この記事を読む前に、以下の記事を読んでおくと理解が深まります。
同相成分と直交成分とは
ひとつのブランコを2人で押すたとえ
IQ変調の本質をつかむために、まず日常的なイメージから入りましょう。一定の周期で揺れているブランコを思い浮かべてください。このブランコを、2人の人が別々のタイミングで押すとします。1人目はブランコが最も手前に来た瞬間(位相の基準点)に押し、2人目はそれよりちょうど4分の1周期遅れた瞬間(ブランコが真ん中を通過する瞬間)に押すとします。
この「4分の1周期ずれ」がポイントです。1人目の押す力の強さと、2人目の押す力の強さは、お互いにまったく干渉しません。1人目が強く押してもブランコの「真ん中通過時の速さ」には影響せず、2人目が強く押しても「手前での折り返しの高さ」には影響しないのです。つまり、同じひとつのブランコの運動でありながら、2つの独立した「押し方の強さ」を別々に制御できます。
IQ変調もこれと同じです。同じ周波数の搬送波に対して、位相が90度(4分の1周期)ずれた2つの波 — $\cos\omega t$ と $\sin\omega t$ — を用意し、それぞれに別々の情報を載せます。$\cos$ に載せる成分を 同相成分(In-phase component, I)、$\sin$ に載せる成分を 直交成分(Quadrature component, Q) と呼びます。「直交」という言葉は、後で見るように2つの波が数学的に直交している(内積がゼロになる)ことに由来します。
なぜ2チャネルにできるのか — 直交性の予告
ブランコのたとえで「お互い干渉しない」と述べましたが、これを数学的に保証するのが $\cos$ と $\sin$ の直交性です。1周期にわたって $\cos\omega t$ と $\sin\omega t$ の積を平均すると、ちょうどゼロになります。一方、$\cos\omega t$ 同士、$\sin\omega t$ 同士の積の平均はゼロにならず、有限の値($1/2$)を持ちます。
この性質のおかげで、受信側では「$\cos$ をかけて平均すれば I だけが残り、$\sin$ をかけて平均すれば Q だけが残る」という綺麗な分離が成り立ちます。これがIQ変調の心臓部であり、本記事を通じて繰り返し立ち戻る原理です。
ここまでで I と Q という2つのチャネルの直感をつかみました。次に、それらを搬送波に載せて1本の実信号を作る式を、丁寧に組み立てていきましょう。
IQ変調された実信号の表現
変調信号の定義
送りたい情報は2つあります。同相成分 $I(t)$ と直交成分 $Q(t)$ です。これらは情報を担う「ベースバンド信号」で、搬送波周波数に比べてゆっくり変化する(帯域が狭い)信号だと考えてください。これらを角周波数 $\omega_c = 2\pi f_c$ の搬送波に載せた IQ変調信号は、次のように定義されます。
$$ \begin{equation} s(t) = I(t)\cos(\omega_c t) – Q(t)\sin(\omega_c t) \end{equation} $$
ここで $-\sin$ の前にマイナス符号が付いている点に注目してください。これは慣習的な定義で、後で複素包絡線 $g(t) = I + jQ$ ときれいに対応させるためのものです。$+\sin$ で定義する流儀もありますが、その場合は複素包絡線が $I – jQ$ になるだけで本質は変わりません。本記事ではディジタル通信で最も標準的な $-\sin$ の定義を採用します。
この式が言っていることはシンプルです。$\cos$ という「土台の波」に $I(t)$ の強さで重みをつけ、それと90度ずれた $\sin$ という「もうひとつの土台の波」に $Q(t)$ の強さで重みをつけ、両者を足し合わせる。たったこれだけで、振幅も位相も自在に操れる信号が作れます。
振幅・位相表現との等価性
式(1)は一見すると振幅変調と位相変調を別物として扱っているように見えますが、実は両者を統一的に含んでいます。三角関数の合成公式を使うと、式(1)は単一の余弦波の振幅変調・位相変調として書き直せます。$I(t) = A(t)\cos\phi(t)$、$Q(t) = A(t)\sin\phi(t)$ と置いてみましょう。これは $I, Q$ を極座標で表すことに相当し、$A(t) = \sqrt{I^2 + Q^2}$、$\phi(t) = \arctan(Q/I)$ です。
これを式(1)に代入します。
$$ s(t) = A(t)\cos\phi(t)\cos(\omega_c t) – A(t)\sin\phi(t)\sin(\omega_c t) $$
ここで加法定理 $\cos\alpha\cos\beta – \sin\alpha\sin\beta = \cos(\alpha + \beta)$ を、$\alpha = \omega_c t$、$\beta = \phi(t)$ として右辺に適用します。すると、
$$ \begin{equation} s(t) = A(t)\cos\bigl(\omega_c t + \phi(t)\bigr) \end{equation} $$
という、たいへん見通しのよい形になります。つまりIQ変調信号は、瞬時振幅 $A(t)$ と瞬時位相 $\phi(t)$ を同時に制御した搬送波に他なりません。$I$ と $Q$ という直交2成分で表すか、振幅 $A$ と位相 $\phi$ という極座標で表すかは、同じ信号の2つの見方なのです。
直交2成分(直交座標)の表現が便利なのは、$I$ と $Q$ が線形に独立して足し合わさるため、回路として加算器ひとつで実装でき、また後述の分離も線形演算で済むからです。一方、振幅・位相(極座標)の表現は、信号の物理的な意味(どれくらいの強さで、どの位相か)を直感的に表します。
ここまでで送信信号の形が定まりました。では受信側で、ひとつの実信号 $s(t)$ から、混ざり合った $I(t)$ と $Q(t)$ をどうやって取り出すのでしょうか。その鍵が直交性です。
直交性による I/Q 分離の導出
cos と sin の直交性
分離の原理を支える数学的事実を、まず正確に述べておきます。搬送波の1周期 $T = 2\pi/\omega_c$ にわたる時間平均を考えます。次の3つの積分が成り立ちます。
$$ \frac{1}{T}\int_0^T \cos^2(\omega_c t)\, dt = \frac{1}{2} $$
$$ \frac{1}{T}\int_0^T \sin^2(\omega_c t)\, dt = \frac{1}{2} $$
$$ \frac{1}{T}\int_0^T \cos(\omega_c t)\sin(\omega_c t)\, dt = 0 $$
最初の2つは、$\cos^2\theta = (1 + \cos 2\theta)/2$ の平均をとると定数項 $1/2$ だけが残ることから出ます。3つ目は、$\cos\theta\sin\theta = \frac{1}{2}\sin 2\theta$ の1周期平均がゼロになることから出ます。3つ目の式が「$\cos$ と $\sin$ は直交している」という主張で、I/Q分離の決め手になります。
これらの平均操作を実際の受信機で行うのが「ローパスフィルタ(LPF)」です。後で見るように、受信信号に $\cos$ や $\sin$ をかけると、欲しい成分(直流近傍のゆっくりした成分)と、不要な成分($2\omega_c$ の高い周波数で振動する成分)が現れます。LPF は前者を通し後者を遮断するので、結果的に「1周期平均をとる」のとほぼ同じ効果になります。
同相成分の取り出し
それでは I を取り出してみましょう。受信した $s(t)$ に $\cos(\omega_c t)$ を掛け算します。これを「同相のローカル発振器(local oscillator, LO)との乗算」と呼びます。
$$ s(t)\cos(\omega_c t) = \bigl[I(t)\cos(\omega_c t) – Q(t)\sin(\omega_c t)\bigr]\cos(\omega_c t) $$
右辺を展開すると2つの項に分かれます。
$$ s(t)\cos(\omega_c t) = I(t)\cos^2(\omega_c t) – Q(t)\sin(\omega_c t)\cos(\omega_c t) $$
ここで2つの三角関数の恒等式を使います。第1項には $\cos^2\theta = \dfrac{1 + \cos 2\theta}{2}$ を、第2項には $\sin\theta\cos\theta = \dfrac{\sin 2\theta}{2}$ を適用します。それぞれ代入すると、
$$ s(t)\cos(\omega_c t) = I(t)\cdot\frac{1 + \cos(2\omega_c t)}{2} – Q(t)\cdot\frac{\sin(2\omega_c t)}{2} $$
これを「直流近傍の項(欲しい成分)」と「$2\omega_c$ で振動する項(不要な成分)」に整理します。
$$ \begin{equation} s(t)\cos(\omega_c t) = \underbrace{\frac{1}{2}I(t)}_{\text{ベースバンド}} + \underbrace{\frac{1}{2}\bigl[I(t)\cos(2\omega_c t) – Q(t)\sin(2\omega_c t)\bigr]}_{2\omega_c\text{ 付近の高周波}} \end{equation} $$
右辺の第1項 $\frac{1}{2}I(t)$ は搬送波周波数を含まないゆっくりした成分です。第2項は搬送波の2倍の周波数 $2\omega_c$ の付近に集まる高周波成分です。$I(t), Q(t)$ がベースバンド(狭帯域)であれば、両者は周波数軸上で大きく離れています。したがってローパスフィルタを通すと第2項が除去され、
$$ \mathrm{LPF}\bigl[s(t)\cos(\omega_c t)\bigr] = \frac{1}{2}I(t) $$
が得られます。係数 $1/2$ は増幅で簡単に補正できるので、これで同相成分 $I(t)$ がきれいに復元できました。重要なのは、$Q(t)$ の項が直流成分に一切漏れ込まなかったことです。これはまさに $\cos$ と $\sin$ の直交性(式の第2項に $Q$ が高周波としてしか現れなかったこと)のおかげです。
直交成分の取り出し
同様に Q を取り出すには、受信信号に $-\sin(\omega_c t)$ を掛けます(変調時の符号に合わせています)。
$$ -s(t)\sin(\omega_c t) = -\bigl[I(t)\cos(\omega_c t) – Q(t)\sin(\omega_c t)\bigr]\sin(\omega_c t) $$
展開すると、
$$ -s(t)\sin(\omega_c t) = -I(t)\cos(\omega_c t)\sin(\omega_c t) + Q(t)\sin^2(\omega_c t) $$
第1項に $\cos\theta\sin\theta = \dfrac{\sin 2\theta}{2}$、第2項に $\sin^2\theta = \dfrac{1 – \cos 2\theta}{2}$ を代入します。
$$ -s(t)\sin(\omega_c t) = -I(t)\cdot\frac{\sin(2\omega_c t)}{2} + Q(t)\cdot\frac{1 – \cos(2\omega_c t)}{2} $$
これをベースバンド項と高周波項に整理すると、
$$ \begin{equation} -s(t)\sin(\omega_c t) = \frac{1}{2}Q(t) – \frac{1}{2}\bigl[I(t)\sin(2\omega_c t) + Q(t)\cos(2\omega_c t)\bigr] \end{equation} $$
第1項がベースバンド、第2項が $2\omega_c$ 付近の高周波です。ローパスフィルタで高周波を除去すると、
$$ \mathrm{LPF}\bigl[-s(t)\sin(\omega_c t)\bigr] = \frac{1}{2}Q(t) $$
となり、こちらも $I(t)$ の漏れ込みなしに $Q(t)$ だけが取り出せました。これでIQ復調の数学的な裏付けが完成しました。
整理すると、I/Q分離は次の2ステップで実現されます。第1ステップは受信信号に $\cos$ あるいは $-\sin$ を掛ける「乗算(ミキシング)」、第2ステップは高周波成分を落とす「ローパスフィルタ」です。この2チャネル分の乗算器とフィルタを並べた回路を IQ復調器(直交復調器、quadrature demodulator) と呼びます。
分離の仕組みが見えたところで、これらの操作を一段とエレガントに記述する道具 — 複素数による表現 — を導入しましょう。
複素ベースバンド表現
複素包絡線の導入
ここまで I と Q を別々の実数信号として扱ってきましたが、この2つを複素数の実部と虚部にまとめると、見通しが劇的によくなります。複素包絡線(complex envelope) あるいは 複素ベースバンド信号 を次のように定義します。
$$ \begin{equation} g(t) = I(t) + j\,Q(t) \end{equation} $$
これは複素平面上の1点で、その実軸方向の座標が I、虚軸方向の座標が Q です。極形式で書けば $g(t) = A(t)e^{j\phi(t)}$ で、絶対値 $A(t) = |g(t)| = \sqrt{I^2 + Q^2}$ が瞬時振幅、偏角 $\phi(t) = \arg g(t) = \arctan(Q/I)$ が瞬時位相に対応します。先ほど振幅・位相表現を導いたときの $A, \phi$ と完全に一致していることに注意してください。
実信号と複素包絡線の関係
驚くほど美しいことに、IQ変調信号 $s(t)$ は複素包絡線 $g(t)$ を使ってただ一行で書けます。次の関係を導いてみましょう。複素指数を搬送波に掛けたもの $g(t)e^{j\omega_c t}$ の実部を考えます。オイラーの公式 $e^{j\omega_c t} = \cos\omega_c t + j\sin\omega_c t$ を使い、$g = I + jQ$ を代入して展開すると、
$$ g(t)e^{j\omega_c t} = (I + jQ)(\cos\omega_c t + j\sin\omega_c t) $$
積を展開し、$j^2 = -1$ を用いて実部と虚部に分けます。
$$ g(t)e^{j\omega_c t} = \bigl(I\cos\omega_c t – Q\sin\omega_c t\bigr) + j\bigl(I\sin\omega_c t + Q\cos\omega_c t\bigr) $$
この実部に注目してください。$I\cos\omega_c t – Q\sin\omega_c t$ は、まさに式(1)で定義した $s(t)$ そのものです。したがって、
$$ \begin{equation} s(t) = \mathrm{Re}\bigl\{g(t)\,e^{j\omega_c t}\bigr\} \end{equation} $$
が成り立ちます。この一行が、IQ変調の理論全体を凝縮した式です。読み解くと、「複素包絡線 $g(t)$ という低周波の複素信号を、$e^{j\omega_c t}$ という回転ベクトルで搬送波周波数まで持ち上げ(周波数シフトし)、その実部を取って実在の電波にする」という操作を表しています。
$-\sin$ の符号を式(1)で採用した理由がここで明らかになります。この符号のおかげで複素包絡線がちょうど $I + jQ$ という自然な形になり、$e^{+j\omega_c t}$ という素直な回転と対応します。もし $+\sin$ で定義していたら、$g = I – jQ$ あるいは $e^{-j\omega_c t}$ という複素共役が現れ、扱いがやや煩雑になります。
復調も複素数で一行に
復調操作も複素表現で簡潔に書けます。受信信号 $s(t)$ に複素 LO $e^{-j\omega_c t}$ を掛けてみます。$s(t) = \mathrm{Re}\{g e^{j\omega_c t}\} = \frac{1}{2}(g e^{j\omega_c t} + g^* e^{-j\omega_c t})$(実部の定義)を代入すると、
$$ s(t)e^{-j\omega_c t} = \frac{1}{2}\bigl(g e^{j\omega_c t} + g^* e^{-j\omega_c t}\bigr)e^{-j\omega_c t} = \frac{1}{2}g(t) + \frac{1}{2}g^*(t)e^{-j2\omega_c t} $$
第1項 $\frac{1}{2}g(t)$ はベースバンド(直流近傍)、第2項は $-2\omega_c$ で回転する高周波です。ローパスフィルタで第2項を落とせば、
$$ \mathrm{LPF}\bigl[s(t)e^{-j\omega_c t}\bigr] = \frac{1}{2}g(t) = \frac{1}{2}\bigl(I(t) + jQ(t)\bigr) $$
となり、複素包絡線が一括で復元されます。この複素信号の実部が I、虚部が Q です。$e^{-j\omega_c t} = \cos\omega_c t – j\sin\omega_c t$ なので、実部の計算は $s(t)\cos\omega_c t$、虚部の計算は $-s(t)\sin\omega_c t$ に対応し、先ほど実数で導いた2本の式とぴたり一致します。複素表現は2つの実数演算を1つの複素演算にまとめているだけで、中身は同じものなのです。
複素ベースバンドという言語を手に入れたことで、IQ変調器・復調器の全体像をブロック図として描き、各部の役割を整理できます。次にその回路構成を見ていきましょう。
IQ変調器・復調器の構成
IQ変調器のブロック構成
IQ変調器(直交変調器)は、式(1)をそのまま回路にしたものです。構成要素は次の通りです。
- ローカル発振器(LO)が搬送波 $\cos\omega_c t$ を生成する
- 90度移相器(位相シフタ)が LO から $\sin\omega_c t$ を作る($\cos$ を90度遅らせると $\sin$ になる)
- I チャネル: ベースバンド信号 $I(t)$ と $\cos\omega_c t$ をミキサ(乗算器)で掛ける
- Q チャネル: ベースバンド信号 $Q(t)$ と $-\sin\omega_c t$ をミキサで掛ける
- 加算器が両チャネルの出力を足し合わせ、$s(t) = I\cos\omega_c t – Q\sin\omega_c t$ を出力する
この構成の要は、LO を90度ずらした2系統を用意し、それぞれに別々のベースバンド信号を載せて足し合わせる点です。LO の周波数はひとつしか使っていないのに、独立した2チャネルが運べることが、帯域効率の良さの源泉です。
IQ復調器のブロック構成
IQ復調器(直交復調器)は、変調器の逆操作を行います。
- 受信信号 $s(t)$ を2つに分配する
- I チャネル: 分配された $s(t)$ に $\cos\omega_c t$ を掛け、ローパスフィルタを通すと $\frac{1}{2}I(t)$ が得られる
- Q チャネル: 分配された $s(t)$ に $-\sin\omega_c t$ を掛け、ローパスフィルタを通すと $\frac{1}{2}Q(t)$ が得られる
- 必要なら2倍に増幅して $I(t), Q(t)$ を復元する
このように、変調も復調も「2系統のミキサ+90度移相器」という対称的な構造で実現できます。受信側で2つのミキサ出力を「I 軸」「Q 軸」として複素平面にプロットしたものが、後述するコンスタレーション図です。
ダイレクトコンバージョン方式
LO の周波数を受信したい搬送波周波数にぴったり合わせ、一気にベースバンド(直流近傍)まで落とすこの方式を ダイレクトコンバージョン(直接変換、ゼロIF) と呼びます。中間周波数(IF)を経由しないため、フィルタや部品が少なく小型・低コストになり、現代のスマートフォンや SDR の主流です。
ただしダイレクトコンバージョンには弱点もあります。I と Q のチャネルでアナログ部品(ミキサ、移相器、アンプ、AD変換器)の特性が完全に一致しないと、後述する「IQ不平衡」という歪みが生じます。理想的には I と Q のゲインが等しく位相差がちょうど90度であるべきですが、現実には微小な誤差が避けられません。この誤差がどんな悪影響を及ぼすかは、本記事の後半で詳しく分析します。
回路の全体像が見えたところで、IQ平面という考え方がディジタル変調とどう結びつくのかを見ていきましょう。ここが「帯域を使い切る」という本記事のテーマの核心です。
QAM・PSK との関係 — IQ平面上の点配置
シンボルは複素平面上の点である
ディジタル通信では、送りたいビット列を「シンボル」という単位に区切り、各シンボルに対して特定の $(I, Q)$ の値を割り当てます。つまり1シンボルは複素包絡線 $g = I + jQ$ の特定の値、すなわち IQ平面(複素平面)上の1点 に対応します。この点の集合を コンスタレーション(信号点配置, constellation) と呼びます。
考え方を逆転させると分かりやすいでしょう。IQ変調器は任意の $(I, Q)$ を搬送波に載せられます。ならば、$(I, Q)$ をいくつかの離散的な値に限定し、それぞれにビットパターンを対応させれば、ディジタル情報を送れます。受信側は復調して得た $(I, Q)$ がどの信号点に最も近いかを判定し、対応するビットを読み出します。これがあらゆるディジタル変調の基本原理です。
PSK — 位相だけを変える
PSK(位相偏移変調, Phase Shift Keying) は、振幅 $A = |g|$ を一定に保ち、位相 $\phi = \arg g$ だけを離散的に変える方式です。信号点はすべて原点を中心とする同一円周上に並びます。
- BPSK: 位相を $0, \pi$ の2値にする。信号点は $(I, Q) = (+1, 0), (-1, 0)$ の2点。1シンボル1ビット
- QPSK: 位相を $\pi/4, 3\pi/4, 5\pi/4, 7\pi/4$ の4値にする。信号点は単位円上に45度間隔で4点。1シンボル2ビット
QPSK の信号点を具体的に書くと、$\left(\pm\frac{1}{\sqrt 2}, \pm\frac{1}{\sqrt 2}\right)$ の4点です。これは「I の符号で1ビット、Q の符号でもう1ビット」を独立に送っていると見ることもできます。まさに直交2チャネルの恩恵で、BPSK を I 軸と Q 軸に2つ重ねたものが QPSK だと理解できます。同じ帯域で2倍のビットを運べるわけです。
QAM — 振幅と位相の両方を変える
QAM(直交振幅変調, Quadrature Amplitude Modulation) は、I と Q をそれぞれ複数の振幅レベルに離散化し、IQ平面上に格子状の信号点を配置する方式です。
- 16QAM: I が $\{-3, -1, +1, +3\}$ の4値、Q も同じく4値。組み合わせで $4\times 4 = 16$ 点。1シンボル4ビット
- 64QAM: I, Q がそれぞれ8値。$8\times 8 = 64$ 点。1シンボル6ビット
- 256QAM: I, Q がそれぞれ16値。$16\times 16 = 256$ 点。1シンボル8ビット
信号点の数 $M$ を増やすほど、1シンボルで運べるビット数 $\log_2 M$ が増え、帯域あたりの伝送速度(周波数利用効率)が上がります。これが「帯域を使い切る」という本記事のタイトルの意味です。ただし信号点が密集するほど、雑音で隣の点に誤判定されやすくなるため、高い信号対雑音比(SNR)が要求されます。5G やケーブルモデムが 256QAM や 1024QAM を使えるのは、それだけ高品質な伝送路が確保できているからです。
QAM も PSK も、結局は「IQ平面のどこに点を置くか」という設計問題に帰着します。この統一的な視点を与えてくれるのが、まさにIQ直交変調の枠組みです。QAM の詳しい話は QAM変調 — 直交振幅変調の原理とコンスタレーション で扱っています。
ここで複素ベースバンドの考え方をもう少し深掘りすると、ヒルベルト変換や解析信号という別の重要概念とつながっていることが見えてきます。次にその接点を整理しましょう。
ヒルベルト変換・解析信号との接点
実信号から複素包絡線を取り戻す問題
これまでは「I と Q が既知で、そこから $s(t)$ を作る/$s(t)$ から I と Q に戻す」という流れを見てきました。では、もし手元に実信号 $s(t)$ しかなく、しかも搬送波の位相基準(LO)が手に入らない場合、複素包絡線をどう復元すればよいでしょうか。ここで登場するのが 解析信号(analytic signal) と ヒルベルト変換 です。
実信号 $s(t)$ のフーリエスペクトルは、正の周波数成分と負の周波数成分が複素共役の関係で対称に存在します。負の周波数成分は、正の成分が決まれば自動的に決まるので、情報としては冗長です。そこで負の周波数成分を取り除き、正の周波数成分だけを残した複素信号を作ります。これが解析信号 $s_a(t)$ で、
$$ \begin{equation} s_a(t) = s(t) + j\,\hat{s}(t) \end{equation} $$
と書けます。ここで $\hat{s}(t)$ は $s(t)$ の ヒルベルト変換 で、すべての周波数成分の位相を $-90$ 度ずらす($\cos \to \sin$、$\sin \to -\cos$ に変換する)操作です。周波数領域では、ヒルベルト変換は伝達関数 $-j\,\mathrm{sgn}(f)$ を掛けることに相当します。
解析信号と複素包絡線の関係
解析信号が複素包絡線とどう結びつくかを見てみましょう。$s(t) = A(t)\cos(\omega_c t + \phi(t))$ の場合、ベースバンドが搬送波に比べて十分ゆっくり変化する(狭帯域)という条件のもとで、ヒルベルト変換は $\hat{s}(t) \approx A(t)\sin(\omega_c t + \phi(t))$ となります。これらを式(8)に代入すると、
$$ s_a(t) = A(t)\cos(\omega_c t + \phi) + jA(t)\sin(\omega_c t + \phi) = A(t)e^{j(\omega_c t + \phi)} $$
となります。最後にオイラーの公式でまとめました。さらに搬送波の回転 $e^{j\omega_c t}$ をくくり出すと、
$$ s_a(t) = \underbrace{A(t)e^{j\phi(t)}}_{=\,g(t)}\,e^{j\omega_c t} = g(t)\,e^{j\omega_c t} $$
つまり、解析信号は「複素包絡線 $g(t)$ を搬送波で回転させたもの」に他なりません。逆に言えば、解析信号に $e^{-j\omega_c t}$ を掛けて搬送波の回転を打ち消せば、複素包絡線が直接得られます。
$$ g(t) = s_a(t)\,e^{-j\omega_c t} $$
これは、ヒルベルト変換さえできれば、$\cos$ と $\sin$ の2系統のミキサを物理的に用意しなくても、デジタル信号処理だけで複素包絡線を取り出せることを意味します。SDR で実信号をサンプリングしてからソフトウェアで I/Q を生成する手法の理論的根拠が、まさにこの解析信号です。ヒルベルト変換の詳細は ヒルベルト変換と解析信号 — 瞬時振幅・瞬時位相を取り出す を参照してください。
解析信号の視点を得たことで、「正の周波数だけを残す」という操作とIQ変調が表裏一体であることが分かりました。この「正・負の周波数の対称性」という観点は、次に扱うIQ不平衡の問題でも決定的な役割を果たします。
IQ不平衡 — 像信号とコンスタレーション歪み
IQ不平衡とは
これまでは I チャネルと Q チャネルが完全に対称(同じゲイン、ちょうど90度の位相差)であると仮定してきました。しかし現実のアナログ回路では、2つのミキサのゲインがわずかに異なったり、90度移相器の位相が正確に90度からずれたりします。この不完全性を IQ不平衡(IQ imbalance) と呼びます。IQ不平衡は復調された複素包絡線を歪ませ、通信品質を劣化させます。
不平衡を2つのパラメータでモデル化しましょう。ゲイン不平衡 $\epsilon$ は I と Q のゲイン比のずれ、位相不平衡 $\Delta\phi$ は90度からの位相ずれです。簡単のため I チャネルを基準にとり、Q チャネルにのみ誤差が乗るとモデル化すると、復調器が使う2つの LO は次のようになります。
$$ \text{I 用: } \cos(\omega_c t), \qquad \text{Q 用: } -(1+\epsilon)\sin(\omega_c t + \Delta\phi) $$
理想状態は $\epsilon = 0$、$\Delta\phi = 0$ です。これらがゼロでないとき、復調された I と Q がどう歪むかを調べます。
歪んだ複素包絡線の導出
送信した複素包絡線を $g = I + jQ$ とし、上記の不平衡のある復調器で取り出される歪んだ I, Q をそれぞれ $\tilde I, \tilde Q$ とします。理想復調では $\tilde I = I$、$\tilde Q = Q$ ですが、不平衡があるとどうなるかを見ます。
I チャネルは理想のままなので $\tilde I = I$ です。問題は Q チャネルです。Q 用 LO は振幅が $(1+\epsilon)$ 倍、位相が $\Delta\phi$ ずれています。復調(乗算+LPF)を行うと、位相ずれにより I 成分が Q チャネルに漏れ込みます。詳しい計算(加法定理で $\sin(\omega_c t + \Delta\phi) = \sin\omega_c t\cos\Delta\phi + \cos\omega_c t\sin\Delta\phi$ を展開し、各項にLPFを適用する)を経ると、
$$ \tilde Q = (1+\epsilon)\bigl(Q\cos\Delta\phi + I\sin\Delta\phi\bigr) $$
が得られます。ここで $\sin\Delta\phi$ の項が、本来 Q だけであるべきところに I を混ぜ込んでいる「漏話(クロストーク)」です。位相不平衡 $\Delta\phi$ がゼロならこの項は消えます。整理すると、歪んだ複素包絡線 $\tilde g = \tilde I + j\tilde Q$ は、
$$ \tilde g = I + j(1+\epsilon)\bigl(Q\cos\Delta\phi + I\sin\Delta\phi\bigr) $$
となります。これは $g$ と $g^*$(複素共役)の線形結合に書き直せます。$I = \frac{g + g^*}{2}$、$Q = \frac{g – g^*}{2j}$ を代入して整理すると、
$$ \begin{equation} \tilde g(t) = \mu\, g(t) + \nu\, g^*(t) \end{equation} $$
という形にまとまります。係数 $\mu, \nu$ は不平衡パラメータ $\epsilon, \Delta\phi$ から定まる複素定数です。理想状態($\epsilon=0, \Delta\phi=0$)では $\mu = 1$、$\nu = 0$ となり $\tilde g = g$、すなわち無歪みに戻ります。
像信号(イメージ)の発生
式(9)の第2項 $\nu g^*(t)$ が、IQ不平衡が引き起こす本質的な問題です。複素共役 $g^*$ は、周波数領域では $g$ のスペクトルを周波数軸で反転させた(正負を入れ替えた)ものに対応します。したがって、もし送信信号が搬送波より高い周波数 $+f_m$ の成分を持っていたとすると、復調後には $-f_m$ の位置に偽の成分が現れます。この偽信号を 像信号(イメージ, image) と呼びます。
像信号は、本来あるべきでない鏡像の周波数に漏れ出すエネルギーです。たとえば隣接チャネルの信号がイメージとして自分のチャネルに重なれば、深刻な干渉になります。像信号の抑圧比(イメージリジェクション比, IRR)は不平衡の大きさで決まり、近似的に
$$ \text{IRR} \approx \left|\frac{\mu}{\nu}\right|^2 \approx \frac{4}{\epsilon^2 + (\Delta\phi)^2} $$
程度になります($\epsilon, \Delta\phi$ が小さいときの近似で、$\Delta\phi$ はラジアン)。たとえば位相誤差が1度(約0.017 rad)、ゲイン誤差が1%($\epsilon=0.01$)の場合、IRR はおよそ $4/(0.01^2 + 0.017^2) \approx 1.1\times 10^4$、すなわち約40 dB です。高品質な通信にはさらに高い IRR が要求されるため、IQ不平衡の補正(キャリブレーション)が実機では不可欠です。
コンスタレーションの歪み
像信号の発生を、ディジタル変調のコンスタレーション図で見ると直感的です。式(9)の $\nu g^*$ 項は、信号点の配置を「ある軸に沿って引き伸ばし、別の軸に沿って縮める」「格子を平行四辺形にゆがめる」といった変形をもたらします。理想なら正方格子に並ぶべき 16QAM の信号点が、ゲイン不平衡では長方形に、位相不平衡では平行四辺形(菱形)に歪みます。
この歪みのせいで、本来離れているはずの信号点同士が近づき、雑音がなくても誤判定が起きやすくなります。受信機の誤り率(BER)が悪化する直接の原因です。だからこそ、現代の受信機はパイロット信号や統計的手法を使って $\mu, \nu$ を推定し、式(9)を逆に解いて $g = (\mu^* \tilde g – \nu \tilde g^*)/(|\mu|^2 – |\nu|^2)$ のように $g$ を復元する「IQ不平衡補正」を行っています。
理論はここまでで一通り揃いました。あとは実際に Python で変調・復調を行い、コンスタレーションを描き、IQ不平衡を注入して像と歪みを目で確かめましょう。
Python による実装
IQ変調と復調の確認
まず、ランダムな I, Q のベースバンド信号を作り、式(1)で変調して実信号 $s(t)$ を生成し、IQ復調器で元の I, Q を復元できることを確認します。ベースバンド信号には帯域制限のためのなだらかな波形を使い、搬送波周波数をその数倍に設定します。
import numpy as np
import matplotlib.pyplot as plt
# サンプリング設定
fs = 20000.0 # サンプリング周波数 [Hz]
T = 0.05 # 観測時間 [s]
t = np.arange(0, T, 1/fs)
fc = 2000.0 # 搬送波周波数 [Hz]
wc = 2 * np.pi * fc
# ベースバンド信号 I(t), Q(t)(搬送波より十分ゆっくり変化)
fm_i, fm_q = 80.0, 130.0 # ベースバンドの周波数 [Hz]
I = np.cos(2 * np.pi * fm_i * t) # 同相成分
Q = 0.6 * np.sin(2 * np.pi * fm_q * t) # 直交成分
# IQ変調: s(t) = I cos(wc t) - Q sin(wc t)
s = I * np.cos(wc * t) - Q * np.sin(wc * t)
ここまでで送信信号 $s(t)$ が出来ました。$I(t)$ と $Q(t)$ はわざと異なる周波数・振幅にしてあり、復調後に両者がきちんと分離して戻るかを見分けやすくしています。
続いて復調を行います。受信信号に $\cos$ と $-\sin$ を掛け、ローパスフィルタ(ここでは簡単な移動平均でなく、周波数領域での理想 LPF を使用)に通します。
# 乗算(ミキシング)
mix_i = s * np.cos(wc * t) # I チャネル
mix_q = -s * np.sin(wc * t) # Q チャネル
# 周波数領域の理想ローパスフィルタ
def lowpass(x, fs, fcut):
"""fcut [Hz] 以下だけを通す理想LPF"""
X = np.fft.rfft(x)
freqs = np.fft.rfftfreq(len(x), 1/fs)
X[freqs > fcut] = 0.0
return np.fft.irfft(X, n=len(x))
fcut = 500.0 # 搬送波(2000Hz)とベースバンド(<=130Hz)の間に設定
I_rec = 2 * lowpass(mix_i, fs, fcut) # 係数1/2を補正
Q_rec = 2 * lowpass(mix_q, fs, fcut)
掛け算で生じる $2f_c = 4000$ Hz 付近の高周波成分を、カットオフ500 Hz の LPF が除去し、ベースバンドだけを残します。係数の $1/2$ は2倍して補正しています。次に元の信号と復元信号を重ねて描画します。
fig, axes = plt.subplots(2, 1, figsize=(10, 6), sharex=True)
axes[0].plot(t * 1e3, I, 'k-', lw=2, label='original I')
axes[0].plot(t * 1e3, I_rec, 'r--', lw=1.5, label='recovered I')
axes[0].set_ylabel('I component')
axes[0].legend(loc='upper right'); axes[0].grid(alpha=0.3)
axes[1].plot(t * 1e3, Q, 'k-', lw=2, label='original Q')
axes[1].plot(t * 1e3, Q_rec, 'b--', lw=1.5, label='recovered Q')
axes[1].set_ylabel('Q component'); axes[1].set_xlabel('time [ms]')
axes[1].legend(loc='upper right'); axes[1].grid(alpha=0.3)
plt.suptitle('IQ Modulation / Demodulation', fontweight='bold')
plt.tight_layout(); plt.savefig('iq_modem.png', dpi=150); plt.show()
このグラフから、復元された I(赤破線)と Q(青破線)が、元の I, Q(黒実線)にほぼ完全に重なっていることが読み取れます。$I$ と $Q$ が異なる周波数・振幅であるにもかかわらず、両者が混ざることなく別々に復元できているのは、$\cos$ と $\sin$ の直交性が機能している何よりの証拠です。端の方でわずかにずれが見えるのは、有限長の信号に理想 LPF を適用したことによる端点効果(リンギング)で、十分長い信号や窓関数を使えば軽減できます。
コンスタレーションの描画
次に、QPSK と 16QAM のコンスタレーションを生成して描画します。ランダムなビット列をシンボルに割り当て、IQ平面上に信号点を配置します。
import numpy as np
import matplotlib.pyplot as plt
rng = np.random.default_rng(0)
N = 2000 # シンボル数
# QPSK: I,Q を ±1/√2 から選ぶ
qpsk_I = rng.choice([-1, 1], N) / np.sqrt(2)
qpsk_Q = rng.choice([-1, 1], N) / np.sqrt(2)
qpsk = qpsk_I + 1j * qpsk_Q
# 16QAM: I,Q を {-3,-1,1,3} から選ぶ
levels = np.array([-3, -1, 1, 3])
qam_I = rng.choice(levels, N)
qam_Q = rng.choice(levels, N)
qam16 = qam_I + 1j * qam_Q
# 受信側の雑音を加える(AWGN)
def add_noise(sym, snr_db):
p_sig = np.mean(np.abs(sym)**2)
p_noise = p_sig / (10**(snr_db/10))
noise = np.sqrt(p_noise/2) * (rng.standard_normal(len(sym))
+ 1j*rng.standard_normal(len(sym)))
return sym + noise
qpsk_rx = add_noise(qpsk, 15)
qam16_rx = add_noise(qam16, 25)
雑音電力を SNR から逆算し、複素ガウス雑音を信号に加えています。実部・虚部それぞれに $\sqrt{P_n/2}$ の標準偏差を割り当てるのは、複素雑音の全電力が $P_n$ になるようにするためです。これを散布図にします。
fig, axes = plt.subplots(1, 2, figsize=(11, 5))
axes[0].scatter(qpsk_rx.real, qpsk_rx.imag, s=5, alpha=0.4, color='tab:blue')
axes[0].set_title('QPSK (SNR=15 dB)')
axes[1].scatter(qam16_rx.real, qam16_rx.imag, s=5, alpha=0.4, color='tab:red')
axes[1].set_title('16QAM (SNR=25 dB)')
for ax in axes:
ax.axhline(0, color='gray', lw=0.5); ax.axvline(0, color='gray', lw=0.5)
ax.set_xlabel('I'); ax.set_ylabel('Q'); ax.set_aspect('equal')
ax.grid(alpha=0.3)
plt.suptitle('Constellation Diagrams', fontweight='bold')
plt.tight_layout(); plt.savefig('iq_constellation.png', dpi=150); plt.show()
左の QPSK は4つの信号点が単位円上に45度間隔で並び、各点の周りに雑音による「雲」が広がっています。右の 16QAM は4×4の正方格子状に16点が並びます。ここから読み取れる重要な点は、16QAM の方が信号点が密集しているため、同じ大きさの雑音でも隣の点に誤判定されやすいということです。だからこそ 16QAM は QPSK より高い SNR(ここでは25 dB対15 dB)を必要とします。点の数を増やせばビット数は増えますが、その分だけ伝送路の品質が問われるという、帯域効率とロバスト性のトレードオフが視覚的に表れています。
IQ不平衡の注入と像信号
最後に、IQ不平衡を注入してコンスタレーションの歪みと像信号を可視化します。まずコンスタレーションへの影響を見ます。式(9)に対応する歪みを 16QAM 信号に適用します。
import numpy as np
import matplotlib.pyplot as plt
rng = np.random.default_rng(1)
N = 3000
levels = np.array([-3, -1, 1, 3])
g = rng.choice(levels, N) + 1j * rng.choice(levels, N) # 理想 16QAM
def apply_imbalance(g, eps, dphi_deg):
"""ゲイン不平衡 eps と位相不平衡 dphi に基づく IQ歪み"""
dphi = np.deg2rad(dphi_deg)
I = g.real
Q = g.imag
I_t = I
Q_t = (1 + eps) * (Q * np.cos(dphi) + I * np.sin(dphi))
return I_t + 1j * Q_t
g_ideal = apply_imbalance(g, 0.0, 0.0) # 無歪み
g_gain = apply_imbalance(g, 0.30, 0.0) # ゲイン不平衡のみ
g_phase = apply_imbalance(g, 0.0, 20.0) # 位相不平衡のみ
ゲイン不平衡だけ、位相不平衡だけ、という極端なケースをわざと作りました(実機よりずっと大きい値で、歪みを見やすくしています)。3つを並べて描画します。
fig, axes = plt.subplots(1, 3, figsize=(14, 4.5))
data = [(g_ideal, 'ideal'), (g_gain, 'gain imbalance eps=0.3'),
(g_phase, 'phase imbalance 20deg')]
for ax, (gg, title) in zip(axes, data):
ax.scatter(gg.real, gg.imag, s=8, alpha=0.5, color='tab:purple')
ax.set_title(title); ax.set_xlabel('I'); ax.set_ylabel('Q')
ax.set_aspect('equal'); ax.grid(alpha=0.3)
ax.axhline(0, color='gray', lw=0.5); ax.axvline(0, color='gray', lw=0.5)
plt.suptitle('IQ Imbalance Distortion of 16QAM', fontweight='bold')
plt.tight_layout(); plt.savefig('iq_imbalance.png', dpi=150); plt.show()
左の理想ケースでは信号点が正方格子に整然と並びます。中央のゲイン不平衡では、Q 軸方向(縦)が引き伸ばされ、格子が長方形に変形しています。これはゲインが I と Q で違うため、片方の軸のスケールだけが変わるからです。右の位相不平衡では、格子が平行四辺形(菱形)にゆがんでいます。これは式(9)で導いた I の Q への漏れ込み($\sin\Delta\phi$ 項)が、Q 軸を傾けることに対応します。いずれの歪みも、信号点同士を近づけて誤判定を招くことが見て取れます。
次に、像信号(イメージ)を周波数領域で確認します。搬送波より高い周波数 $+f_m$ にだけスペクトルを持つ複素正弦波 $g(t)=e^{j2\pi f_m t}$ を入力し、IQ不平衡を通したときに $-f_m$ に像が現れるかを見ます。
import numpy as np
import matplotlib.pyplot as plt
fs = 10000.0
t = np.arange(0, 0.2, 1/fs)
fm = 600.0
g = np.exp(1j * 2 * np.pi * fm * t) # +fm のみに成分を持つ複素信号
def imbalance_complex(g, eps, dphi_deg):
dphi = np.deg2rad(dphi_deg)
I, Q = g.real, g.imag
Q_t = (1 + eps) * (Q * np.cos(dphi) + I * np.sin(dphi))
return I + 1j * Q_t
g_dist = imbalance_complex(g, 0.10, 8.0) # ゲイン10%・位相8度の不平衡
# スペクトル(両側)
def spectrum(x, fs):
X = np.fft.fftshift(np.fft.fft(x)) / len(x)
f = np.fft.fftshift(np.fft.fftfreq(len(x), 1/fs))
return f, 20*np.log10(np.abs(X) + 1e-12)
f0, S0 = spectrum(g, fs)
f1, S1 = spectrum(g_dist, fs)
plt.figure(figsize=(10, 5))
plt.plot(f0, S0, 'k-', lw=1.5, label='ideal (no image)')
plt.plot(f1, S1, 'r-', lw=1.5, alpha=0.8, label='with IQ imbalance')
plt.axvline(fm, color='green', ls=':', label='signal +fm')
plt.axvline(-fm, color='orange', ls=':', label='image -fm')
plt.xlim(-1500, 1500); plt.ylim(-80, 5)
plt.xlabel('frequency [Hz]'); plt.ylabel('magnitude [dB]')
plt.title('Image Signal due to IQ Imbalance'); plt.legend(); plt.grid(alpha=0.3)
plt.tight_layout(); plt.savefig('iq_image.png', dpi=150); plt.show()
黒線(理想)では $+600$ Hz に単一のピークだけが立ち、負の周波数側には何もありません。これは複素信号が片側スペクトルを持つことの確認です。一方、赤線(IQ不平衡あり)では $+600$ Hz の本来のピークに加えて、$-600$ Hz の位置に小さなピーク(像信号)が現れています。これがまさに式(9)の $\nu g^*$ 項が生んだ鏡像です。像のピークと本来のピークの高さの差が、イメージリジェクション比(IRR)に相当します。ここでは約21 dB(近似式 $4/(\varepsilon^2+\Delta\phi^2)$ でも実測でも約21 dB)で、ゲイン10%・位相8度という比較的大きな不平衡を反映しています。不平衡を小さくすれば像も小さくなり、IRR が改善することが、この図から定量的に理解できます。
まとめ
本記事では、IQ直交変調を直感・数式の導出・Python実装の3つの角度から解説しました。要点を振り返ります。
- 直交2成分: 同相成分 $I$ と直交成分 $Q$ を、90度ずれた $\cos\omega_c t$ と $\sin\omega_c t$ にそれぞれ載せ、$s(t)=I\cos\omega_c t – Q\sin\omega_c t$ という1本の実信号にまとめる
- 直交性による分離: 受信信号に $\cos$ や $-\sin$ を掛けてローパスフィルタに通すと、$\cos$ と $\sin$ の直交性により I と Q が漏れ込みなく分離できる
- 複素ベースバンド: 複素包絡線 $g=I+jQ$ を導入すると、変調は $s=\mathrm{Re}\{g\,e^{j\omega_c t}\}$、復調は $g=\mathrm{LPF}[s\,e^{-j\omega_c t}]$ という一行で表せる
- QAM/PSK: ディジタル変調は IQ平面上のどこに信号点を置くかという設計問題であり、点を増やすほど帯域効率が上がるがSNR要求も厳しくなる
- ヒルベルト変換との接点: 解析信号 $s_a=s+j\hat s = g\,e^{j\omega_c t}$ を通じて、実信号からソフトウェアだけで複素包絡線を取り出せる
- IQ不平衡: ゲイン・位相誤差は歪んだ包絡線 $\tilde g=\mu g+\nu g^*$ を生み、$\nu g^*$ 項が像信号とコンスタレーション歪みをもたらす
IQ直交変調は、AM・FM といったアナログ変調と、QAM・PSK・OFDM といったディジタル変調をつなぐ「共通言語」です。ここで身につけた複素ベースバンドの考え方は、ディジタル変調の誤り率解析、SDR の信号処理、レーダーのドップラー処理、ビームフォーミングまで、電波通信のあらゆる場面で繰り返し使うことになります。
次のステップとして、以下の記事も参考にしてください。