在上次的程序中,已经实现好了基类的搭建,现在实现一种最简单的编码方式。
编码方式为:在数据的头部和尾部加入:01111110,在数据中,只要出现5个1,就在后面添加0。
问题的一个难点在于:变化之后的数据很可能不再是8的整数倍,我将最后的几个位空出来,设置为0,来凑齐8的整数位。此类命名为:SimpleCoder,在coder.h中实现,总的coder.h代码如下:
// coder.h
#ifndef CODER_H
#define CODER_H
#include "datareader.h"
#include <iostream>
#include <vector>
class Coder
{
protected:
unsigned char* storage;
int size;
int length;
DataReader& data;
int prtlen;
public:
Coder(DataReader* dr) : data(*dr)
{
storage = data.storage;
size = data.size;
length = data.length;
prtlen = size * length;
}
void update()
{
storage = data.storage;
size = data.size;
length = data.length;
prtlen = size * length;
}
DataReader& getDataReader()
{
return data;
}
// This print function show how to show the magic memory.
// But I will use the real magic memory method,
// because it's easy to code and decode.
/*std::ostream& print(std::ostream& out)
{
for (int i = 0; i < length; i++)
for (int j = size - 1; j >= 0; j--)
for(int k = 7; k >= 0; k--)
if (storage[i * size + j] & (1 << k))
out << 1;
else
out << 0;
return out;
}*/
std::ostream& print(std::ostream& out)
{
for (int i = 0; i < prtlen; i++)
for (int j = 7; j >= 0; j--)
if (storage[i] & (1 << j))
out << 1;
else
out << 0;
return out;
}
void print()
{
print(std::cout);
}
virtual void code() {}
//virtual void decode() = 0;
};
std::ostream& operator<<(std::ostream& out, Coder& coder) {
return coder.print(out);
}
class SimpleCoder : public Coder
{
void addFlag(std::vector<unsigned short>& data)
{
data.push_back(0);
for (int i = 0; i < 6; i++)
data.push_back(1);
data.push_back(0);
}
public:
SimpleCoder(DataReader* dr) : Coder(dr){}
void code()
{
std::vector<unsigned short> data;
addFlag(data);
int count = 0;
for (int i = 0; i < prtlen; i++)
for (int j = 7; j >= 0; j--)
{
if (count == 5)
{
data.push_back(0);
count = 0;
}
if (storage[i] & (1 << j))
{
data.push_back(1);
count++;
} else {
data.push_back(0);
count = 0;
}
}
addFlag(data);
unsigned char* store = new unsigned char[data.size() / 8 + 1];
for (int i = 0; i < data.size() / 8 + 1; i++)
{
store[i] = 0;
for (int j = 7; j >= 0; j--)
if (7 - j + 8 * i < data.size())
store[i] |= (data[7 - j + 8 * i] << j);
}
delete [] storage;
storage = store;
prtlen = data.size() / 8 + 1;
}
};
#endif
测试代码如下:
//test.cpp
#include <iostream>
#include "coder.h"
using namespace std;
int main()
{
int a[] = {1, 4, -1};
SimpleCoder coder(new DataReader(a, 3));
cout << coder << endl;
coder.code();
cout << coder << endl;
DataReader& dr = coder.getDataReader();
dr.setStorage('a');
coder.update();
cout << coder << endl;
char s[] = "aaaab";
dr.setStorage(s, 6);
coder.update();
cout << coder << endl;
return 0;
}
运行结果: