苏泊尔耗的JPEG解码器[二]

哈夫曼解码和位流操作部分。

JPEG的哈夫曼编码是优化过的,对于每一个N位长的编码只要它小于MAX[N]就是一个结束编码。MAX[N]可根据DHT语法中给出的码表算出。

取位的方法很普通。如果用汇编优化的话,可以考虑用以前跟踪到的某H-GAME中图片解码程序的实现方法。在这里就不多讲了。

要注意的是RSTn可能会穿插在这里面。

jpeghuff.h

********************************************** 低调滴分隔线(1) ***************************************

/**************************************************************************************************

  superarhow's JPEG decoder

  by superarhow(superarhow@hotmail.com).  All rights reserved.

 **************************************************************************************************/

#pragma once

#include "JpegDec2.h"

/* 从流中读下一个哈夫曼编码并解码出其对应的字节 */
BYTE jpeg_dec_next_huff_code(p_jpeg_dec_rec p_rec, p_jpeg_huff_table p_table);

/* 从流中读取n_bits位 */
WORD jpeg_get_next_bits(p_jpeg_dec_rec p_rec, BYTE n_bits); 

********************************************** 低调滴分隔线(2) ***************************************

jpeghuff.c

********************************************** 低调滴分隔线(3) ***************************************

/**************************************************************************************************

  superarhow's JPEG decoder

  by superarhow(superarhow@hotmail.com).  All rights reserved.

 **************************************************************************************************/

#include "jpegdec2.h"

/*
 *  从流中读下一个哈夫曼编码并解码出其对应的字节
 *  返回解码出的字节
 */
BYTE jpeg_dec_next_huff_code(p_jpeg_dec_rec p_rec, p_jpeg_huff_table p_table)
{
 WORD *p_min_code, *p_max_code;
 BYTE *p_codedata, *p_startindexes;
 BYTE *p_data;
 BYTE left_bits, n_left_bit_count, mask;
 WORD code;

 p_min_code  = p_table->huff_min_codes;
 p_max_code  = p_table->huff_max_codes;
 p_codedata  = p_table->start_code_indexes;
 p_startindexes = p_table->start_code_indexes;

 p_data = p_rec->p_data;
 left_bits = p_rec->left_bits;
 n_left_bit_count = p_rec->n_left_bit_count;
 mask = 1 << (n_left_bit_count - 1);
 code = 0;
 for ( ;; ) {
  if ( n_left_bit_count == 0 ) {
   /* fetch the next bits from the stream */
   n_left_bit_count = 8;
   mask = 0x80;
   left_bits = *p_data++;
   while ( left_bits == 0xFF ) {
    if ( *p_data == 0 ) {
     p_data++;
     break;
    } else if ( *p_data >= 0xD0 && *p_data <= 0xD7 ) {
     /* RSTn */
     n_left_bit_count = 0;
     jpeg_reset(p_rec);
     ++p_data;
     break;
    } else {
     left_bits = *p_data++;
     break;
    }
   }
   if ( n_left_bit_count == 0 ) continue; /* still not get the next byte :( */
  }
  code = code << 1;
  if ( left_bits & mask ) code++;
  n_left_bit_count--;
  left_bits &= (~mask);
  if ( code <= *p_max_code && (*p_max_code >= 0x8000 || 0x8000 >= *p_min_code) ) {
   /* Done! */
   break;
  }
  p_max_code++;
  p_min_code++;
  p_codedata++;
  p_startindexes++;
  mask >>= 1;
 }
 p_rec->n_left_bit_count = n_left_bit_count;
 p_rec->left_bits = left_bits;
 p_rec->p_data = p_data;
 code -= *p_min_code;
 if (code + *p_startindexes >= p_table->n_code_count) _asm int 3;
 return p_table->codes[code + *p_startindexes];
}

/*
 *  从流中读取n_bits位
 *  返回读取的位码
 */
WORD jpeg_get_next_bits(p_jpeg_dec_rec p_rec, BYTE n_bits)
{
 WORD result;
 BYTE *p_data;
 BYTE left_bits, n_left_bit_count;

 result = 0;
 p_data = p_rec->p_data;
 left_bits = p_rec->left_bits;
 n_left_bit_count = p_rec->n_left_bit_count;

 while ( n_bits > 0 ) {

  if ( n_left_bit_count == 0 ) {
   /* fetch the next bits from the stream */
   n_left_bit_count = 8;
   left_bits = *p_data++;
   while ( left_bits == 0xFF ) {
    if ( *p_data == 0 ) {
     ++p_data;
     break;
    } else if ( *p_data >= 0xD0 && *p_data <= 0xD7 ) {
     /* RSTn */
     n_left_bit_count = 0;
     jpeg_reset(p_rec);
     ++p_data;
     break;
    } else {
     left_bits = *p_data++;
     break;
    }
   }
   if ( n_left_bit_count == 0 ) continue; /* still not get the next byte :( */
  }

  if ( n_left_bit_count >= n_bits ) {
   /* fetch n_bits bits */
   n_left_bit_count -= n_bits;
   result <<= n_bits;
   result |= ( ((1 << n_bits) - 1) & (left_bits >> n_left_bit_count) );
   break;
  } else {
   /* fetch n_left_bit_count bits */
   result <<= n_left_bit_count;
   result |= ( ((1 << n_left_bit_count) - 1) & left_bits );
   n_bits -= n_left_bit_count;
   n_left_bit_count = 0;
  }
 }
 /* set the changed pointer and bit values */
 p_rec->left_bits = left_bits;
 p_rec->n_left_bit_count = n_left_bit_count;
 p_rec->p_data = p_data;
 return result;
}

********************************************** 低调滴分隔线(4) ***************************************

基于bert实现关系三元组抽取python源码+数据集+项目说明.zip基于bert实现关系三元组抽取python源码+数据集+项目说明.zip基于bert实现关系三元组抽取python源码+数据集+项目说明.zip基于bert实现关系三元组抽取python源码+数据集+项目说明.zip基于bert实现关系三元组抽取python源码+数据集+项目说明.zip 个人大四的毕业设计、课程设计、作业、经导师指导并认可通过的高分设计项目,评审平均分达96.5分。主要针对计算机相关专业的正在做毕设的学生和需要项目实战练习的学习者,也可作为课程设计、期末大作业。 [资源说明] 不懂运行,下载完可以私聊问,可远程教学 该资源内项目源码是个人的毕设或者课设、作业,代码都测试ok,都是运行成功后才上传资源,答辩评审平均分达到96.5分,放心下载使用! 1、该资源内项目代码都经过测试运行成功,功能ok的情况下才上传的,请放心下载使用! 2、本项目适合计算机相关专业(如计科、人工智能、通信工程、自动化、电子信息等)的在校学生、老师或者企业员工下载学习,也适合小白学习进阶,当然也可作为毕设项目、课程设计、作业、项目初期立项演示等。 3、如果基础还行,也可在此代码基础上进行修改,以实现其他功能,也可用于毕设、课设、作业等。 下载后请首先打开README.md文件(如有),供学习参考。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值