m0_52762547 2023-06-07 22:34 采纳率: 100%

香农解码的代码问题，无法输出解码结果

#请问这段代码为什么无法输出解码的结果
#

``````text = 'abracadabra';  % 待编码的文本
[encoded, decoded, avgCodeLength, efficiency] = shannonCoding(text);
disp('编码结果：');
disp(encoded);
disp('解码结果：');
disp(decoded);
disp('平均码长：');
disp(avgCodeLength);
disp('编码效率：');
disp(efficiency);

function [encoded, decoded, avgCodeLength, efficiency] = shannonCoding(text)
% 计算字符频率
symbols = unique(text);
freq = zeros(size(symbols));
for i = 1:length(symbols)
freq(i) = sum(text == symbols(i));
end
freq = freq / numel(text);

% 计算累积概率
cumProb = cumsum(freq);

% 构建编码表
codeTable = cell(length(symbols), 2);
for i = 1:length(symbols)
codeTable{i, 1} = symbols(i);
codeTable{i, 2} = ''; % 初始化编码为空
end

% 递归构建编码表
codeTable = buildCodeTable(codeTable, cumProb, 1, '');

% 编码
encoded = '';
for i = 1:numel(text)
symbol = text(i);
index = find(strcmp(codeTable(:, 1), symbol));
code = codeTable{index, 2};
encoded = [encoded, code];
end

% 解码
decoded = '';
code = '';
for i = 1:numel(encoded)
code = code + encoded(i);
index = find(strcmp(codeTable(:, 2), code));
if ~isempty(index)
symbol = codeTable{index, 1};
decoded = [decoded, symbol];
code = '';
end
end

% 计算平均码长
codeLengths = cellfun(@length, codeTable(:, 2));
avgCodeLength = sum(codeLengths .* freq);

% 计算编码效率
efficiency = 1 ./ avgCodeLength;
end

% 递归构建编码表
function codeTable = buildCodeTable(codeTable, cumProb, index, code)
if index > length(codeTable)
return;
end

if cumProb(index) <= 0.5
codeTable{index, 2} = [code, '0'];
codeTable = buildCodeTable(codeTable, cumProb, index+1, [code, '0']);
else
codeTable{index, 2} = [code, '1'];
codeTable = buildCodeTable(codeTable, cumProb, index+1, [code, '1']);
end
end
```c

``````
``````#输出结果如下，解码结果那一行无内容输出

```c

00101111001100111001011110

6.8182    2.7273    1.3636    1.3636    2.7273

0.1467    0.3667    0.7333    0.7333    0.3667

``````

`````` % 解码
decoded = '';
code = '';
for i = 1:numel(encoded)
code = code + encoded(i);
index = find(strcmp(codeTable(:, 2), code));
if ~isempty(index)
symbol = codeTable{index, 1};
else//新加入的
decoded = [decoded, symbol];
code = '';
end
end

``````

• 写回答

4条回答默认 最新

• 大师兄6668 Python领域新星创作者 2023-06-07 22:53
关注

你这个我逐步打印了一下，确定了问题确实在解码环节，解码的算法写的不对。

``````codeTable: [['w', '0'], ['l', '00'], ['h', '000'], ['r', '0001'], ['o', '00011'], ['d', '000111'], ['e', '0001111']]
encoded: 0000001111000000011000011000100000111

``````

这是打印出来的字典和编码后的字符，这里是OK的。
然后你解码的时候，是针对编码的字符挨个取出来去进行判断是否和字典中的编码一样，这里就要注意了，
由于每个字母编码时候的字典位数并不相等，但是你取编码字符的时候是逐个取的，然后和它进行比较判断的，一旦字典中的位数不是1，那你解码就会失败，就会变成空白。
并且，你这个同一个字符串，每次运行的时候，生成的字典是不同的，所以每次解码出来的结果也不一样，但是都有一个特点就是，最多只能解码出来一个字母，或者这个字母的重复
需要修改你的解码逻辑方可解决，但是位数不一样，不太好改，我正在研究。
如果可以的话，可以连编码带解码一并修改，这样比较好弄。
盼回复，一起交流。

本回答被题主选为最佳回答 , 对您是否有帮助呢?
评论 编辑记录

• 系统已结题 6月16日
• 已采纳回答 6月8日
• 创建了问题 6月7日

悬赏问题

• ¥15 Qt4代码实现下面的界面
• ¥15 prism提示我reinstall prism 如何解决
• ¥15 asp.core 权限控制怎么做，需要控制到每个方法
• ¥20 while循环中OLED显示中断中的数据不正确
• ¥15 这个视频里的stm32f4代码是怎么写的
• ¥15 JNA调用DLL报堆栈溢出错误（0xC00000FD）
• ¥15 请教SGeMs软件的使用
• ¥15 自己用vb.net编写了一个dll文件，如何只给授权的用户使用这个dll文件进行打包编译，未授权用户不能进行打包编译操作？
• ¥50 深度学习运行代码直接中断
• ¥20 需要完整的共散射点成像代码