Virtual.cpp

#include <iostream>
#include <fstream>
#include <string>
#include <stdlib.h>
#include <stdio.h>

class MField
{
public:
	MField() { m_bNULL = false; m_nSize = 0; }
	MField( const char* Name, int Size )
	{
		m_sName = Name;
		m_nSize = Size;
		m_bNULL = true;
	}
	bool IsNull() const { return( m_bNULL ); }
	void SetNull() { m_bNULL = true; }
	string GetName() const { return( m_sName ); }

	virtual string GetAsString() const =0;
	virtual void SetFromString( const string& Src )=0;

	virtual bool SaveTo( ofstream& Dest ) const =0;
	virtual bool LoadFrom( ifstream& Src ) =0;

	virtual void Dump( ostream& Dest)
	{
		Dest << "MField: m_sName="<<m_sName<<" m_nSize=" << m_nSize;
		Dest << " m_bNULL=" << (m_bNULL?"TRUE":"FALSE") << endl;  
	}
protected:
	int m_nSize;
	string m_sName;
	bool m_bNULL;
};


class MIntField : public MField
{
public:
	MIntField( const char* Name ) : MField( Name, sizeof(m_nValue) )
	{
		m_nValue = 0; // Not really important
	}
	string GetAsString() const{
		char Tmp[16];
		sprintf( Tmp, "%d", m_nValue );
		return( string( Tmp ) );
	}
	void SetFromString( const string& Src ) {
		m_nValue = atoi( Src.c_str() );
		m_bNULL = false;
	}
        bool SaveTo( ofstream& Dest ) const
	{
        	Dest.write( (void*)&m_nValue, sizeof(m_nValue) );
		return Dest.good();
	}
        bool LoadFrom( ifstream& Src )
	{
        	Src.read( (void*)&m_nValue, sizeof(m_nValue) );
		return Src.good();
	}
	void Dump( ostream& Dest )
	{
		MField::Dump( Dest );
		Dest << "MIntField:  m_nValue=" << m_nValue << endl;
	}
protected:
	int m_nValue;

};

class MFloatField : public MField
{
public:
	MFloatField( const char* Name ) : MField( Name, sizeof(m_fValue) )
	{
		m_fValue = 0.0; // Not really important
	}
	string GetAsString() const {
		char Tmp[16];
		sprintf( Tmp, "%f", m_fValue );
		return( string( Tmp ) );
	}
	void SetFromString( const string& Src ) {
		m_fValue = atof( Src.c_str() );
		m_bNULL = false;
	}

        bool SaveTo( ofstream& Dest ) const
	{
        	Dest.write( (void*)&m_fValue, sizeof(m_fValue) );
		return Dest.good();
	}
        bool LoadFrom( ifstream& Src )
	{
        	Src.read( (void*)&m_fValue, sizeof(m_fValue) );
		return Src.good();
	}
	void Dump( ostream& Dest )
	{
		MField::Dump( Dest );
		Dest << "MFloatField: m_fValue="<<m_fValue<<endl;
	}
protected:
	double m_fValue;

};
	
/////////////////////////////////////////////////////////////////////
void Populate( MField* Record[] )
{
	string Data;
	for( int i=0; Record[i];  i++)
	{
		cout << "Enter value for " << Record[i]->GetName() << endl;
		getline( cin, Data );
		Record[i]->SetFromString( Data );
	}
}

void Show( MField** Record )
{
	for( int i=0; Record[i]; i++ )
		cout << "Field " << Record[i]->GetName() << ": " << Record[i]->GetAsString() << endl;
}

int main()
{
	MField* Record[3];
	
	Record[0] = new MIntField( "ID" );
	Record[1] = new MFloatField( "Pay" );
	Record[2] = 0;

        Populate( Record );
	Show( Record );
	Record[0]->Dump( cout );
	return(0);
}