## Documentation Center |

`decoded = vitdec(code,trellis,tblen,opmode,dectype)`

decoded = vitdec(code,trellis,tblen,opmode,'soft',nsdec)

decoded = ...

vitdec(code,trellis,tblen,opmode,dectype,puncpat)

decoded = ...

vitdec(code,trellis,tblen,opmode,dectype,puncpat,eraspat)

decoded = ...

vitdec(...,'cont',...,initmetric,initstates,initinputs)

[decoded,finalmetric,finalstates,finalinputs] = ...

vitdec(...,'cont',...)

`decoded = vitdec(code,trellis,tblen,opmode,dectype)` decodes
the vector

The string * opmode* indicates the decoder's
operation mode and its assumptions about the corresponding encoder's
operation. Choices are in the table below.

**Values of opmode Input**

Value | Meaning |
---|---|

'cont' | The encoder is assumed to
have started at the all-zeros state. The decoder traces back from
the state with the best metric. A delay equal to tblen symbols
elapses before the first decoded symbol appears in the output. This
mode is appropriate when you invoke this function repeatedly and want
to preserve continuity between successive invocations. See the continuous operation mode syntaxes below. |

'term' | The encoder is assumed to
have both started and ended at the all-zeros state, which is true
for the default syntax of the convenc function.
The decoder traces back from the all-zeros state. This mode incurs
no delay. This mode is appropriate when the uncoded message (that
is, the input to convenc) has enough zeros at
the end to fill all memory registers of the encoder. If the encoder
has k input streams and constraint length vector constr (using
the polynomial description of the encoder), "enough"
means k*max(constr-1). |

'trunc' | The encoder is assumed to have started at the all-zeros state. The decoder traces back from the state with the best metric. This mode incurs no delay. This mode is appropriate when you cannot assume the encoder ended at the all-zeros state and when you do not want to preserve continuity between successive invocations of this function. |

For the ** 'term'** and

The string * dectype* indicates the
type of decision that the decoder makes, and influences the type of
data the decoder expects in

**Values of dectype Input**

Value | Meaning |
---|---|

'unquant' | code contains
real input values, where 1 represents a logical zero and -1 represents
a logical one. |

'hard' | code contains
binary input values. |

'soft' | For soft-decision decoding,
use the syntax below. nsdec is required for soft-decision
decoding. |

`decoded = vitdec(code,trellis,tblen,opmode,'soft',nsdec)` decodes
the vector

`decoded = ... vitdec(code,trellis,tblen,opmode,dectype,puncpat)` denotes
the input punctured

`decoded = ... vitdec(code,trellis,tblen,opmode,dectype,puncpat,eraspat)` allows
an erasure pattern vector,

Continuous operation mode enables you to save the decoder's internal state information for use in a subsequent invocation of this function. Repeated calls to this function are useful if your data is partitioned into a series of smaller vectors that you process within a loop, for example.

`decoded = ... vitdec(...,'cont',...,initmetric,initstates,initinputs) ` is
the same as the earlier syntaxes, except that the decoder starts with
its state metrics, traceback states, and traceback inputs specified
by

`[decoded,finalmetric,finalstates,finalinputs] = ...
vitdec(...,'cont',...)` is the same
as the earlier syntaxes, except that the final three output arguments
return the state metrics, traceback states, and traceback inputs,
respectively, at the end of the decoding process.

The *t*^{th} column
of *P*_{1} shows the *t*-1^{th} time
step states given the inputs listed in the input matrix. For example,
the value in the *i*^{th} row
shows the state at time *t*-1 that transitions to
the *i*-1 state at time *t*. The
input required for this state transition is given in the *i*^{th} row
of the *t*^{th} column of
the input matrix.

The *P*_{1} output is the
states of the traceback matrix. It is a [number of states x traceback
length] matrix. The following example uses a (7,5), rate 1/2 code.
This code is easy to follow:

t = poly2trellis(3,[7 5]);

k = log2(t.numInputSymbols);

msg = [1 1 0 0 1 1 0 0 1 1 0 0 1 1 0 0 1 1 0 0 1
1 0 0 1 1 0 0 1 1 0 0];

code = convenc(msg,t); tblen
= 15; [d1 m1 p1 in1]=vitdec(code(1:end/2),t,tblen,'cont','hard')

m1 = 0 3 2 3

p1 = 0 1 1 0 0 1 1 0 0 1 1 0 0 1 1 2 3 3 2 2 3 3 2 2 3 3 2 2 3 3 0 1 1 0 0 1 1 0 0 1 1 0 0 1 1 2 3 3 2 2 3 3 2 2 3 3 2 2 3 3

in1 = 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1

In this example, the message makes the encoder states follow the following sequence:

0 2 3 1 / 0 2 3 1 / ...

Since the best state is `0` (column index of
smallest metric in *m*_{1} –1),
the traceback matrix starts from sate `0`, looking
at the first row (`0`^{th} state)
of the last column of *P*_{1},
([1; 3; 1; 3]), which is `1`. This indicates `1` for
the previous state.

Next, the traceback matrix checks in1 ([0; 0; 1; 1]), which
indicates `0` for the input. The second row (1st
state) of the 14^{th} column of *P*_{1} ([1;
3; 1; 3]) is `3`. This indicates `3` for
the previous state.

The traceback matrix checks in1 ([0; 0; 1; 1]), which indicates
that the input was 0. The fourth row (3rd state) of the 13th column
of *P*_{1} ([0; 2; 0; 2]), is `2`.
This indicates `2` for the previous state.

The traceback matrix checks in1 ([0; 0; 1; 1]), which indicates
the input was `1`. The third row (2nd state) of
the 12th column of *P*_{1} ([0;
2; 0; 2]), is `0`. This indicates `0` for
the previous state.

The traceback matrix checks in1 ([0; 0; 1; 1]), which indicates
the input was `1`. The first row (0th state) of
the 11th column of *P*_{1} ([1;
3; 1; 3]), is `1`. This indicates `1` for
the previous state. Then, the matrix checks in1 ([0; 0; 1; 1]), which
indicates `0` for the input.

To determine the best state for a gicen time, use *m*_{1}.
The smallest number in *m*_{1} represents
the best state.

The example below encodes random data and adds noise. Then it
decodes the noisy code three times to illustrate the three decision
types that `vitdec` supports. For unquantized and
soft decisions, the output of `convenc` does not
have the same data type that `vitdec` expects for
the input code, so it is necessary to manipulate `ncode` before
invoking `vitdec`. That the bit error rate computations
must account for the delay that the continuous operation mode incurs.

s = RandStream.create('mt19937ar', 'seed',131); prevStream = RandStream.setGlobalStream(s); % seed for repeatability trel = poly2trellis(3,[6 7]); % Define trellis. msg = randi([0 1],100,1); % Random data code = convenc(msg,trel); % Encode. ncode = rem(code + randerr(200,1,[0 1;.95 .05]),2); % Add noise. tblen = 3; % Traceback length decoded1 = vitdec(ncode,trel,tblen,'cont','hard'); %Hard decision % Use unquantized decisions. ucode = 1-2*ncode; % +1 & -1 represent zero & one, respectively. decoded2 = vitdec(ucode,trel,tblen,'cont','unquant'); % To prepare for soft-decision decoding, map to decision values. [x,qcode] = quantiz(1-2*ncode,[-.75 -.5 -.25 0 .25 .5 .75],... [7 6 5 4 3 2 1 0]); % Values in qcode are between 0 and 2^3-1. decoded3 = vitdec(qcode',trel,tblen,'cont','soft',3); % Compute bit error rates, using the fact that the decoder % output is delayed by tblen symbols. [n1,r1] = biterr(decoded1(tblen+1:end),msg(1:end-tblen)); [n2,r2] = biterr(decoded2(tblen+1:end),msg(1:end-tblen)); [n3,r3] = biterr(decoded3(tblen+1:end),msg(1:end-tblen)); disp(['The bit error rates are: ',num2str([r1 r2 r3])]) RandStream.setGlobalStream(prevStream); % restore default stream

The following example illustrates how to use the final state
and initial state arguments when invoking `vitdec` repeatedly. `[decoded4;decoded5]` is
the same as `decoded6`.

s = RandStream.create('mt19937ar', 'seed',131); % seed for repeatability prevStream = RandStream.setGlobalStream(s); trel = poly2trellis(3,[6 7]); code = convenc(randi([0 1],100,1),trel); % Decode part of code, recording final state for later use. [decoded4,f1,f2,f3] = vitdec(code(1:100),trel,3,'cont','hard'); % Decode the rest of code, using state input arguments. decoded5 = vitdec(code(101:200),trel,3,'cont','hard',f1,f2,f3); % Decode the entire code in one step. decoded6 = vitdec(code,trel,3,'cont','hard'); isequal(decoded6,[decoded4; decoded5]) RandStream.setGlobalStream(prevStream); % restore default stream

For additional examples, see Convolutional Codes.

For some commonly used puncture patterns for specific rates and polynomials, see the last three references below.

[1] Clark, G. C. Jr. and J. Bibb Cain., *Error-Correction
Coding for Digital Communications*, New York, Plenum Press,
1981.

[2] Gitlin, Richard D., Jeremiah F. Hayes,
and Stephen B. Weinstein, *Data Communications Principles*,
New York, Plenum, 1992.

[3] Heller, J. A. and I. M. Jacobs, "Viterbi
Decoding for Satellite and Space Communication," *IEEE
Transactions on Communication Technology*, Vol. COM-19,
October 1971, pp 835–848.

[4] Yasuda, Y., et. al., "High rate
punctured convolutional codes for soft decision Viterbi decoding," *IEEE
Transactions on Communications*, vol. COM-32, No. 3, pp
315–319, Mar. 1984.

[5] Haccoun, D., and G. Begin, "High-rate
punctured convolutional codes for Viterbi and sequential decoding," *IEEE
Transactions on Communications*, vol. 37, No. 11, pp 1113–1125,
Nov. 1989.

[6] G. Begin, et.al., "Further results
on high-rate punctured convolutional codes for Viterbi and sequential
decoding," *IEEE Transactions on Communications*,
vol. 38, No. 11, pp 1922–1928, Nov. 1990.

Was this topic helpful?