几年前的东西,空间换时间的东西就不多解释了。
/**********************************XXXXXX.h*****************************************/
#define MAX_VALUE_SIZE (0x00FFFFFF)
#define MAX_NUMBER_SIZE (256)
#define MAX_FILE_SIZE (32)
#define MAX_PI_VALUE (3.141592f)
#define MAX_STRING_SIZE (5U)
#define MAX_STRING_LEN (16)
enum _flag {
_failure,
_success
};
enum _find_flag {
_not = 1,
_cur,
_inv
};
/***************************************************************************/
struct _file_data {
FILE * _hfile;
char _file_name[MAX_FILE_SIZE];
};
struct _file_info {
int _count;
struct _file_data _da[MAX_FILE_SIZE];
};
//保存的客户信息
struct _user_db {
char _user[MAX_STRING_LEN];
};
//全局扩展数据结构
struct _str_data {
bool _first;
_user_db * _retval;
char _in_str[MAX_FILE_SIZE];
struct _file_info _file;
};
/***************************************************************************/
int _init_str(void);
void _free_str(void);
int _fastcall _ins_str(const char * str);
int _fastcall _del_str(const char * str);
static int _fastcall _strtoint1(const char * str,size_t _nlen);
static int _fastcall _strtoint2(const char * str,size_t _nlen);
static int _fastcall _strtoint3(const char * str,size_t _nlen);
static int _fastcall _strtoint4(const char * str,size_t _nlen);
static int _fastcall _strtoint5(const char * str,size_t _nlen);
static int _fastcall _strtoint6(const char * str,size_t _nlen);
static int _fastcall _strtoint7(const char * str,size_t _nlen);
int _fastcall _find_str(const char * str);
static int _fastcall _pop_str(int _val,size_t _nlen);
static int _push_str(int _val,const char * str,size_t _nlen);
static int _ins_file(char * _val,const char * _fname,const char * str);
static int _find_file(const char * _fname,const char * str);
static int _sear_str(FILE * _hfile,char * _val,const char * str);
/***************************************************************************/
/***************************************************************************/
__volatile static _str_data _gda = {{0}};
/***************************************************************************/
#define _OPERATION1(_x,_y,_z,_a,_i,_l,_c) {(_z) = (_a); \
(_x) = (_z) * ((_z) * (_i)); \
(_y) = (_x) % (_l); \
(_y) = (_y) ^ 0x01FFFF + ((_a) + (_i)); \
(_c) += static_cast<float>((_x) * MAX_PI_VALUE - ((_z) + (_l) + (_z) * (_l)) + (_y)); }
/***************************************************************************/
#define _OPERATION2(_x,_y,_z,_a,_i,_l,_c) {(_z) = (_a); \
(_x) = (_z) * ((_z) * (_i)); \
(_y) = (_x) % (_l); \
(_c) += static_cast<float>((_x) * MAX_PI_VALUE - ((_z) + (_l) + (_z) * (_l)) + (_y)); \
(_c) += static_cast<float>((_a) + (_z) * (_i)); }
/***************************************************************************/
#define _OPERATION3(_x,_y,_z,_a,_i,_l,_c) {(_z) = (_a); \
(_x) = (_z) + (_i); \
(_y) = (_x) % (_l); \
(_y) = (_y) ^ 0x01FFFF + ((_a) + (_i)); \
(_c) += static_cast<float>(((_x) + (_y) + (_a)) * MAX_PI_VALUE); }
/***************************************************************************/
#define _OPERATION4(_x,_y,_z) { \
(_z) += (_y) * (_x); \
(_z) += (_y) * (_x) * 314; \
(_z) += (_x) * 314 + 314 * (_y); \
(_z) = (_z) ^ 0x0FFFF + ((_y) + (_x));\
}
//(_y) += (_y) * 31 + (_x);
/***************************************************************************/
#define _OPERATION5(_x,_y) { \
(_y) += ((_y) + 31 + (_x)) + (_y) % 31; \
}
/***************************************************************************/
#define _OPERATION6(_x,_y,_z) { \
(_z) += ((_x) % 27) * (_y); \
(_z) = (_z) ^ 0x1FF + ((_x) % (_y)); \
}
/***************************************************************************/
#define _OPERATION7(x,y,z) { \
(z) += ((x) * (((x) % (y))) + (y)); \
}
/***************************************************************************/
__volatile static int u = 0;
/**********************************XXXXXX.c*****************************************/
#include "XXXXXX.h"
int _init_str(void)
{
const size_t _nLen = sizeof(struct _user_db) * MAX_VALUE_SIZE;
_gda._retval = (struct _user_db *)malloc(_nLen);
if (_gda._retval != 0) {
memset(_gda._retval,0,_nLen);
memset(_gda._in_str,0,MAX_FILE_SIZE);
memset(&_gda._file,0,sizeof(struct _file_info));
return _success;
}
return 0;
}
void _free_str(void)
{
if (_gda._retval != 0) {
free(_gda._retval);
_gda._retval = 0;
memset(_gda._in_str,0,8);
memset(&_gda._file,0,sizeof(struct _file_info));
}
return;
}
int _fastcall _find_str(const char * str)
{
if (str != 0) {
const size_t _nlen = strnlen(str,MAX_STRING_LEN);
register int _val = _strtoint1(str,_nlen);
if (_val > (-1) && _val < MAX_VALUE_SIZE) {
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
} else {
_val = _strtoint2(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
} else {
_val = _strtoint3(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
} else {
_val = _strtoint4(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
} else {
_val = _strtoint5(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
} else {
_val = _strtoint6(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
} else {
_val = _strtoint7(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("%s\r\n",_gda._retval[_val]._user);
return _success;
}
}
}
}
}
}
}
}
}
return _failure;
}
int _fastcall _del_str(const char * str)
{
if (str != 0) {
const size_t _nlen = strnlen(str,MAX_STRING_LEN);
register int _val = _strtoint1(str,_nlen);
if (_val > (-1) && _val < MAX_VALUE_SIZE) {
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
return _pop_str(_val,_nlen);
} else {
_val = _strtoint2(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
return _pop_str(_val,_nlen);
} else {
_val = _strtoint3(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
return _pop_str(_val,_nlen);
} else {
_val = _strtoint4(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
return _pop_str(_val,_nlen);
} else {
_val = _strtoint5(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
return _pop_str(_val,_nlen);
} else {
_val = _strtoint6(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,_nlen) == 0) {
return _pop_str(_val,_nlen);
} else {
_val = _strtoint7(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,_nlen) == 0) {
return _pop_str(_val,_nlen);
}
}
}
}
}
}
}
}
}
return _failure;
}
int _fastcall _ins_str(const char * str)
{
const size_t _nlen = strlen(str);
if (_nlen > MAX_STRING_SIZE /*&& _off == _find_str(str)*/) {
return _push_str(_strtoint1(str,_nlen),str,_nlen);
} else { return _failure; }
}
static int _sear_str(FILE * _hfile,char * _val,const char * str)
{
const int _nlen = strlen(str);
register char _cmp_str[MAX_NUMBER_SIZE] = {0};
register int _retval = _cur;
if (_nlen <= MAX_NUMBER_SIZE) {
while( !feof( _hfile ) )
{
if (fgets(_cmp_str,MAX_NUMBER_SIZE,_hfile) > 0) {
if (0 == strncmp(str,_cmp_str,_nlen)) {
_retval = _inv;
if (_gda._first != false && (_val != 0 && _val[0] < 0x0FF)) {
_val[0]++;
continue;
}
fseek(_hfile,0L,SEEK_SET);
return _retval;
}
}
}
}
if (_gda._first != true) {
_retval = _cur;
} else {
_gda._first =false;
}
fseek(_hfile,0L,SEEK_SET);
return _retval;
}
static int _ins_file(char * _val,const char * _fname,const char * str)
{
if (str != 0) {
register FILE * _hfile = fopen(_fname,"r+");
if (_hfile != 0) {
_gda._first = true;
_FILE_MAG:
if (_cur == _sear_str(_hfile,_val,str) && fputs(str,_hfile) > (-1)) {
fclose(_hfile);
_val[0] += _success;
return _success;
}
fclose(_hfile);
} else if ((_hfile = fopen(_fname,"a+")) != 0){
goto _FILE_MAG;
}
}
return _failure;
}
static int _find_file(const char * _fname,const char * str)
{
if (str != 0) {
register FILE * _hfile;
const size_t _nlen = strlen(_fname);
for (register unsigned int i = 0U; i < MAX_FILE_SIZE; i++) {
if (strncmp(_gda._file._da[i]._file_name,_fname,_nlen) == 0) {
return _sear_str(_gda._file._da[i]._hfile,0,str);
}
}
_hfile = fopen(_fname,"r");
if (_hfile != 0) {
if (_gda._file._count == MAX_FILE_SIZE) {
_gda._file._count = 0;
}
if (_gda._file._da[_gda._file._count]._hfile != 0) {
fclose(_gda._file._da[_gda._file._count]._hfile);
memset(_gda._file._da[_gda._file._count]._file_name,0,MAX_FILE_SIZE);
}
_gda._file._da[_gda._file._count]._hfile = _hfile;
strncpy(_gda._file._da[_gda._file._count]._file_name,_fname,_nlen);
_gda._file._count++;
return _sear_str(_hfile,0,str);
}
}
return _failure;
}
static int _push_str(int _val,const char * str,size_t _nlen)
{
if ((_val > (-1) && _val < MAX_VALUE_SIZE)) {
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
} else {
_val = _strtoint2(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
} else {
_val = _strtoint3(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
} else {
_val = _strtoint4(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
} else {
_val = _strtoint5(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
} else {
_val = _strtoint6(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
} else {
_val = _strtoint7(str,_nlen);
if (strncmp(_gda._retval[_val]._user,str,MAX_STRING_LEN) == 0) {
printf("重复字串:%s\r\n",str);
return _failure;
} else if (_gda._retval[_val]._user[0] == 0) {
memcpy(_gda._retval[_val]._user,str,_nlen);
return _success;
}
}
}
}
}
}
}
}
u++;
printf("碰撞或溢出 %s,%d,%d\r\n",str,_val,u);
return _failure;
}
static int _fastcall _pop_str(int _val,size_t _nlen)
{
if ((_val > (-1) && _val < MAX_VALUE_SIZE)) {
memset(_gda._retval[_val]._user,0,_nlen);
return _success;
}
return _failure;
}
static int _fastcall _strtoint1(const char * str,size_t _nlen)
{
int s = 0;
unsigned int x,y,z;
register float _count = 0.00000f;
const size_t _slen = (_nlen + 1U);
for (register size_t i = 1U; i < _slen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION1(x,y,z,s,i,_slen,_count);
}
return static_cast<int>(_count);
}
static int _fastcall _strtoint2(const char * str,size_t _nlen)
{
int s = 0;
unsigned int x,y,z;
register float _count = 0.00000f;
const size_t _slen = (_nlen + 1U);
for (register size_t i = 1U; i < _slen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION2(x,y,z,s,i,_slen,_count);
}
return static_cast<int>(_count);
}
static int _fastcall _strtoint3(const char * str,size_t _nlen)
{
int s = 0;
unsigned int x,y,z;
register float _count = 0.00000f;
const size_t _slen = (_nlen + 1U);
for (register size_t i = 1U; i < _slen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION3(x,y,z,s,i,_slen,_count);
}
return static_cast<int>(_count);
}
static int _fastcall _strtoint4(const char * str,size_t _nlen)
{
int s = 0;
register int _count = 0;
for (register size_t i = 0U; i < _nlen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION4(i,s,_count);
}
return (_count);
}
static int _fastcall _strtoint5(const char * str,size_t _nlen)
{
int s = 0;
register int _count = 0;
for (register size_t i = 0U; i < _nlen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION5(s,_count);
}
return (_count);
}
static int _fastcall _strtoint6(const char * str,size_t _nlen)
{
int s = 0;
register int _count = 0;
for (register size_t i = 0U; i < _nlen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION6(i,s,_count);
}
return (_count);
}
static int _fastcall _strtoint7(const char * str,size_t _nlen)
{
int s = 0;
register int _count = 0;
const size_t _slen = (_nlen + 1U);
for (register int i = 1U; i < _slen; i++) {
if ((s = str[i]) < 0) { s *= (-1); }
_OPERATION7(s,i,_count);
}
return (_count);
}
/***************************************************************************/
/**********************************main.c*****************************************/
void _ins(void);
void _ins(void)
{
string str = "abcdefghijklmnopqrstuvwxyz0123456789";
vector<string> str_vector;
//那么就100W个字符串吧
int size = 1000000;
clock_t q = clock();
//生成长度大小为6 - MAX_STRING_LEN之间的随机且不重复字串
for( int i = 0; i < size; i++ )
{
int x = rand() % MAX_STRING_LEN;
while (x < 6) {
x = rand() % MAX_STRING_LEN;
}
random_shuffle( str.begin(), str.end() );
str_vector.push_back( str.substr( 0,x) );
}
vector<string>::iterator it = unique( str_vector.begin(), str_vector.end() );
str_vector.resize( it - str_vector.begin() );
str_vector.resize( size );
clock_t w = clock();
printf("生成随机字符串 time: %d,%d\r\n",w-q,u);
q = clock();
for ( unsigned int i = 0; i < str_vector.size(); i++ ) {
_ins_str(str_vector[ i ].c_str());
}
w = clock();
printf("插入所有字符串 time: %d,%d\r\n",w-q,u);
}
int _tmain(int argc, _TCHAR* argv[])
{
int v = 0;
v = _init_str();
_ins();
system("pause.");
//所有返回值1为成功,0为失败
while (1)
{
char buf[22] = {0};
printf("命令:");
scanf("%s",&buf);
if (*buf == 'i') {
scanf("%s",&buf);
v = _ins_str(buf);
printf("插入 success: %d\r\n",v);
} else if (*buf == 'f') {
scanf("%s",&buf);
clock_t s = clock();
v = _find_str(buf);
clock_t e = clock();
printf("查找 time: %d,success: %d\r\n",e-s,v);
} else if (*buf == 'q') {
_free_str();
return 0;
} else if(*buf == 'd') {
scanf("%s",&buf);
_del_str(buf);
}
}
system("pause.");
_free_str();
return 0;
}
这是一个hash组合方式,功能也就是插入,查找,删除几个简单的方法;其实这东西就是根据字符串得出一个数组的下标,然后保存简短的结构信息,当然,同时也可扩展范围;至于碰撞问题你懂的;
6.14重新测试了100W个随机且不同的字符串,结果如下:
生成随机字符串 time: 117.094s
插入所有字符串 time: 1.046s
出现重复字串(5个):
xq4nua
u349fy
pjqm4g
wm3dz1
swhuga
目测木有碰撞发生,运气好啊~
备注:STL random_shuffle函数也不是绝对的~