⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 table.h

📁 用CJ60Lib界面库制作的SQL数据库客户与服务器程序。
💻 H
字号:
#if !defined(AFX_TABLE_H__81E8846B_3542_47B9_AC4D_91919A3E5133__INCLUDED_)
#define AFX_TABLE_H__81E8846B_3542_47B9_AC4D_91919A3E5133__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

#include "LexAnalyzer.h"
#include "Cache.h"

#include "ClientSocket.h"
#include "ServerDoc.h"
#include "Msg.h"

//////////////////////////////////////////////////////////////
// type definitions
typedef CList< CString, CString& > STR_LIST;
typedef CList< long, long > RESULT;

struct STR_PAIR
{
	STR_LIST first;
	STR_LIST second;
};

//////////////////////////////////////////////////////////////
// type of an item

class CItemType
{
public:
    CItemType( SQLKey idd = _INT, size_t sz = 0 ) : id( idd ), size( sz )
    {
        switch( idd )
        {
            case _INT    : size = sizeof( int );    break;
            case _LONG   : size = sizeof( long );   break;
            case _FLOAT  : size = sizeof( double ); break;
            case _STRING : size = sz + 1;           break;
            case _DATE   : size = sizeof( time_t ); break;
        }
        size += sizeof( bool );
    }
    SQLKey	id;
    size_t	size;
};

//////////////////////////////////////////////////////////////
// item attribute

class CItemAttr
{
public:
    CItemAttr( const char* iname = "", 
		const CItemType& itype = CItemType(), long ioffset = 0 ) :
        type( itype ), offset( ioffset )
    {
        strncpy( name, iname, FIELD_NAME_LEN );
        name[ FIELD_NAME_LEN ] = '\0';
    }

	char		name[ FIELD_NAME_LEN + 1 ];
    CItemType	type;
    long		offset;
};

//////////////////////////////////////////////////////////////
// entry attribute

class CEntryAttr
{
public:
    CEntryAttr() : num( 0 ), length( 0 ) {}
    void      push( const CItemAttr& );
    void      rearrange();
    int       index( const char* ) const;

    CItemAttr	attr[ FIELD_NUM ];
    int			num;
    long		length;
};

//////////////////////////////////////////////////////////////
// the record value

//inline functions
inline	int&    GET_INT( void* p )    {  return *(int*)((char*)p + sizeof(bool));     }
inline  long&   GET_LONG( void* p )   {  return *(long*)((char*)p + sizeof(bool));    }
inline  double& GET_FLOAT( void* p )  {  return *(double*)((char*)p + sizeof(bool));  }
inline  char*   GET_STR( void* p )    {  return  (char*)p + sizeof(bool);             }
inline  time_t& GET_DATE( void* p )   {  return *(time_t*)((char*)p + sizeof(bool));  }
inline  bool&   GET_NULL( void* p )   {  return *(bool*)p;  }

class CValue
{
public:
    CValue( void* vptr, const CItemType& vtype ) : 
	  ptr( vptr ), type( vtype ) {}
	~CValue();

    bool& null() const				//is the record NULL
	{
		return GET_NULL( ptr );
	}

    void   in( const double& );
    void   out( double& ) const;					//store / access double
    void   in( const char* );
    void   out( char*, size_t n = TEMP_SIZE ) const;	//store / access string

    CValue& operator = ( const CValue& rhs )
    {   
        ::memmove( ptr, rhs.ptr, type.size );
        return *this;
    }

	bool operator <  ( const CValue& rhs ) const;
	bool operator == ( const CValue& rhs ) const;

private:
    void* const			ptr;					//point to the record
    const CItemType&	type;
};

//////////////////////////////////////////////////////////////
// one entry

class CEntry
{
public:
	//constructors
	CEntry( const CEntryAttr& eattr ) : 
      ptr( new char[ eattr.length ] ), attr( eattr ), create( true )
    {
		for( int i = 0; i < eattr.num - 1; i++ )
			(*this)[i].null() = true;
	}

    CEntry( void* eptr, const CEntryAttr& eattr ) : 
      ptr( eptr ), attr( eattr ), create( false ) {}

    CEntry( const CEntry& entry ) : 
      ptr( entry.ptr ), attr( entry.attr ), create( entry.create )
	{
		if( create )
			ptr = new char[ attr.length ], *this = entry;
	}
    
	//destructor
	~CEntry()
	{
		if( create )
			delete [] (char*)ptr;
	}

    inline int values() const			//count of the items
    {
		return attr.num;
	}

	//operators
    CEntry& operator = ( const CEntry& rhs )
    {
        memmove( ptr, rhs.ptr, attr.length );
        return *this; 
    }

    CValue operator [] ( int i ) const
    {  
        if( i < 0 || i >= attr.num )
            throw Error( ENTRY_RANGE_ERROR, attr.num, CString("") );
        return CValue( (char*)ptr + attr.attr[i].offset, attr.attr[i].type );
    }

    CValue operator [] ( const char* n ) const
    {
		return operator[]( attr.index(n) );
	}

    char* operator & () const					//return the pointer to the date area
    {
		return (char*)ptr;
	}

    bool operator <  ( const CEntry& ) const;	//alphabet compare
    bool operator == ( const CEntry& ) const;

private:
    void*				ptr;		//pointer to the data
    const CEntryAttr&	attr;		//relation attributes
    bool				create;		//is this newly created ?
};

//////////////////////////////////////////////////////////////
// table attribute

class CTableAttr
{
public:
    int			index_num;										//count of indices
    char		index_table[ INDEX_NUM ][ MAIN_NAME_LEN + 1 ];	//indices names
    CEntryAttr  attr;											//relation attributes
};

//////////////////////////////////////////////////////////////
// the table

class CTable
{
public:
    CTable( const char*, const CEntryAttr& );					//create a table[name|relations]
    CTable( const char* );										//open existed table[name]
    ~CTable();

// operations
public:
	void    create_index( const char*, const STR_LIST&, bool ); // 创建B+树索引[名称|属性名列表|是否候选键]
	void    drop_index( const char* );                          // 删除B+树索引[名称]
	void    insert( const STR_PAIR& );
	void    remove( const RESULT& );
	void    update( const RESULT&, const STR_PAIR& );
	void    select( const RESULT&, const STR_LIST& );

	void	concatenate( STR_PAIR& ret, const STR_PAIR& src );
	void	search( RESULT& );
	void	search( RESULT&, const STR_PAIR& );
	void	search( RESULT&, const STR_PAIR&, const STR_PAIR& );
	void	search( RESULT&, const STR_PAIR&, const STR_PAIR&, const STR_PAIR& );
	void	close();
	void    drop();

	// for socket
	void	search( RESULT&, CClientSocket* pSocket, CServerDoc* pDoc );
	void	search( RESULT&, const STR_PAIR&, CClientSocket* pSocket, CServerDoc* pDoc );
	void	search( RESULT&, const STR_PAIR&, const STR_PAIR&, CClientSocket* pSocket, CServerDoc* pDoc );
	void	search( RESULT&, const STR_PAIR&, const STR_PAIR&, const STR_PAIR&, CClientSocket* pSocket, CServerDoc* pDoc );
	void    select( const RESULT&, const STR_LIST&, CClientSocket* pSocket, CServerDoc* pDoc );
	void	SendCol( CEntryAttr&, CClientSocket* pSocket, CServerDoc* pDoc );
	void	SendItem( CEntry&, CClientSocket* pSocket, CServerDoc* pDoc );
	int		GetLength( const CItemType& type );

private:
	void LoadAttr()
	{
		tableAPI->ReadAttr( &attr, sizeof( CTableAttr ) );
	}

	void SaveAttr()
	{
		tableAPI->WriteAttr( &attr, sizeof( CTableAttr ) );
	}

	void		insert_index( const char* );                        // 在表属性中插入索引名
	void		remove_index( const char* );                        // 从表属性中删除索引名
	int			find_index( const char* );                          // 寻找索引名在表属性中的位置
	CEntryAttr	convert( const STR_LIST& );
	void		convert( CEntry&, const STR_PAIR& );

public:
	CString		m_tname;
	CTableAttr	attr;
	CFileAPI*   tableAPI;
};

#endif // !defined(AFX_TABLE_H__81E8846B_3542_47B9_AC4D_91919A3E5133__INCLUDED_)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -