From 64d9c29568c6593b2a2ea0b7d4eb0152156b3679 Mon Sep 17 00:00:00 2001 From: Glenn Maynard Date: Tue, 11 Oct 2005 10:24:07 +0000 Subject: [PATCH] Simplify: store attributes in a simple map, not in an object. Makes attributes lighter. --- stepmania/src/Actor.cpp | 4 +- stepmania/src/BackgroundUtil.cpp | 2 +- stepmania/src/Font.cpp | 4 +- stepmania/src/IniFile.cpp | 9 +-- stepmania/src/ThemeManager.cpp | 2 +- stepmania/src/TitleSubstitution.cpp | 4 +- stepmania/src/XmlFile.cpp | 105 +++++++++------------------- stepmania/src/XmlFile.h | 70 +++++++------------ 8 files changed, 68 insertions(+), 132 deletions(-) diff --git a/stepmania/src/Actor.cpp b/stepmania/src/Actor.cpp index 3d801d5603..3a32b54dc4 100644 --- a/stepmania/src/Actor.cpp +++ b/stepmania/src/Actor.cpp @@ -222,8 +222,8 @@ void Actor::LoadFromNode( const CString& sDir, const XNode* pNode ) FOREACH_CONST_Attr( pNode, pAttr ) { // Load Name, if any. - const CString &sKeyName = pAttr->m_sName; - const CString &sValue = pAttr->m_sValue; + const CString &sKeyName = pAttr->first; + const CString &sValue = pAttr->second; if( sKeyName == "Name" ) { m_sName = sValue; diff --git a/stepmania/src/BackgroundUtil.cpp b/stepmania/src/BackgroundUtil.cpp index dde34ba4db..ce82af10e3 100644 --- a/stepmania/src/BackgroundUtil.cpp +++ b/stepmania/src/BackgroundUtil.cpp @@ -232,7 +232,7 @@ static void GetFilterToFileNames( const CString sBaseDir, const Song *pSong, set } FOREACH_CONST_Attr( pSection, p ) - vsPossibleFileNamesOut.insert( p->m_sName ); + vsPossibleFileNamesOut.insert( p->first ); } void BackgroundUtil::GetGlobalBGAnimations( const Song *pSong, const CString &sMatch, vector &vsPathsOut, vector &vsNamesOut ) diff --git a/stepmania/src/Font.cpp b/stepmania/src/Font.cpp index 85f4a69948..f7746a789f 100644 --- a/stepmania/src/Font.cpp +++ b/stepmania/src/Font.cpp @@ -406,8 +406,8 @@ void Font::LoadFontPageSettings( FontPageSettings &cfg, IniFile &ini, const CStr { FOREACH_CONST_Attr( pNode, pAttr ) { - CString sName = pAttr->m_sName; - const CString &sValue = pAttr->m_sValue; + CString sName = pAttr->first; + const CString &sValue = pAttr->second; sName.MakeUpper(); diff --git a/stepmania/src/IniFile.cpp b/stepmania/src/IniFile.cpp index 919131d0aa..7c3dfb1e54 100644 --- a/stepmania/src/IniFile.cpp +++ b/stepmania/src/IniFile.cpp @@ -95,7 +95,7 @@ bool IniFile::WriteFile( RageFileBasic &f ) const FOREACH_CONST_Attr( pKey, pAttr ) { - if( f.PutLine( ssprintf("%s=%s", pAttr->m_sName.c_str(), pAttr->m_sValue.c_str()) ) == -1 ) + if( f.PutLine( ssprintf("%s=%s", pAttr->first.c_str(), pAttr->second.c_str()) ) == -1 ) { m_sError = f.GetError(); return false; @@ -124,7 +124,7 @@ void IniFile::SetValue( const CString &keyname, const CString &valuename, const XNode* pNode = GetChild( keyname ); if( pNode == NULL ) pNode = AppendChild( keyname ); - pNode->SetAttrValue( valuename, value ); + pNode->AppendAttr( valuename, value ); } bool IniFile::DeleteValue(const CString &keyname, const CString &valuename) @@ -132,10 +132,7 @@ bool IniFile::DeleteValue(const CString &keyname, const CString &valuename) XNode* pNode = GetChild( keyname ); if( pNode == NULL ) return false; - XAttr* pAttr = pNode->GetAttr( valuename ); - if( pAttr == NULL ) - return false; - return pNode->RemoveAttr( pAttr ); + return pNode->RemoveAttr( valuename ); } diff --git a/stepmania/src/ThemeManager.cpp b/stepmania/src/ThemeManager.cpp index 56b79ccd75..8cd6c692b5 100644 --- a/stepmania/src/ThemeManager.cpp +++ b/stepmania/src/ThemeManager.cpp @@ -775,7 +775,7 @@ void ThemeManager::GetModifierNames( vector& AddTo ) if( cur ) { FOREACH_CONST_Attr( cur, p ) - AddTo.push_back( p->m_sName ); + AddTo.push_back( p->first ); } } } diff --git a/stepmania/src/TitleSubstitution.cpp b/stepmania/src/TitleSubstitution.cpp index b2db05313d..0257b9f7de 100644 --- a/stepmania/src/TitleSubstitution.cpp +++ b/stepmania/src/TitleSubstitution.cpp @@ -50,8 +50,8 @@ void TitleTrans::LoadFromNode( const XNode* pNode ) { /* Surround each regex with ^(...)$, to force all comparisons to default * to being a full-line match. (Add ".*" manually if this isn't wanted.) */ - const CString &sKeyName = attr->m_sName; - const CString &sValue = attr->m_sValue; + const CString &sKeyName = attr->first; + const CString &sValue = attr->second; if( sKeyName == "DontTransliterate" ) translit = false; else if( sKeyName == "TitleFrom" ) TitleFrom = "^(" + sValue + ")$"; else if( sKeyName == "ArtistFrom" ) ArtistFrom = "^(" + sValue + ")$"; diff --git a/stepmania/src/XmlFile.cpp b/stepmania/src/XmlFile.cpp index 6547ea2bee..4fec75c1dd 100644 --- a/stepmania/src/XmlFile.cpp +++ b/stepmania/src/XmlFile.cpp @@ -99,7 +99,7 @@ XNode::XNode( const XNode &cpy ): FOREACH_CONST_Child( &cpy, c ) this->AppendChild( new XNode(*c) ); FOREACH_CONST_Attr( &cpy, a ) - this->AppendAttr( new XAttr(*a) ); + this->AppendAttr( a->first, a->second ); } XNode::~XNode() @@ -112,9 +112,6 @@ void XNode::Clear() FOREACH_Child( this, p ) SAFE_DELETE( p ); m_childs.clear(); - - FOREACH_Attr( this, p2 ) - SAFE_DELETE( p2 ); m_attrs.clear(); } @@ -152,14 +149,14 @@ unsigned XNode::LoadAttributes( const CString &xml, PARSEINFO *pi, unsigned iOff return string::npos; } - XAttr *attr = new XAttr; - // XML Attr Name - SetString( xml, iOffset, iEnd, &attr->m_sName ); + CString sName; + SetString( xml, iOffset, iEnd, &sName ); // add new attribute - DEBUG_ASSERT( attr->m_sName.size() ); - m_attrs.insert( make_pair(attr->m_sName, attr) ); + DEBUG_ASSERT( sName.size() ); + pair it = m_attrs.insert( make_pair(sName, "") ); + CString &sValue = it.first->second; iOffset = iEnd; // XML Attr Value @@ -189,11 +186,11 @@ unsigned XNode::LoadAttributes( const CString &xml, PARSEINFO *pi, unsigned iOff } bool trim = pi->trim_value; - SetString( xml, iOffset, iEnd, &attr->m_sValue, trim ); + SetString( xml, iOffset, iEnd, &sValue, trim ); iOffset = iEnd; // ATTRVALUE if( pi->entity_value ) - ReplaceEntityText( attr->m_sValue, g_mapEntitiesToChars ); + ReplaceEntityText( sValue, g_mapEntitiesToChars ); if( quote == '"' || quote == '\'' ) ++iOffset; @@ -429,12 +426,12 @@ unsigned XNode::Load( const CString &xml, PARSEINFO *pi, unsigned iOffset ) // Desc : convert plain xml text from parsed xml attirbute // Return : converted plain string -bool XAttr::GetXML( RageFileBasic &f, DISP_OPT *opt ) const +bool XNode::GetAttrXML( RageFileBasic &f, DISP_OPT *opt, const CString &sName, const CString &sValue ) const { - CString s(m_sValue); + CString s(sName); if( opt && opt->reference_value ) ReplaceEntityText( s, g_mapCharsToEntities ); - return f.Write(m_sName + "='" + s + "' ") != -1; + return f.Write(sName + "='" + s + "' ") != -1; } // Desc : convert plain xml text from parsed xml node @@ -461,7 +458,7 @@ bool XNode::GetXML( RageFileBasic &f, DISP_OPT *opt ) const if( f.Write(" ") == -1 ) return false; FOREACH_CONST_Attr( this, p ) - if( !p->GetXML(f, opt) ) + if( GetAttrXML(f, opt, p->first, p->second) ) return false; if( m_childs.empty() && m_sValue.empty() ) @@ -543,12 +540,12 @@ void XNode::GetValue( bool &out ) const { out = atoi(m_sValue) != 0; } void XNode::GetValue( unsigned &out ) const { out = 0; sscanf(m_sValue,"%u",&out); } void XNode::GetValue( DateTime &out ) const { out.FromString( m_sValue ); } -void XAttr::GetValue( CString &out ) const { out = m_sValue; } -void XAttr::GetValue( int &out ) const { out = atoi(m_sValue); } -void XAttr::GetValue( float &out ) const { out = strtof(m_sValue, NULL); } -void XAttr::GetValue( bool &out ) const { out = atoi(m_sValue) != 0; } -void XAttr::GetValue( unsigned &out ) const { out = 0; sscanf(m_sValue,"%u",&out); } -void XAttr::GetValue( DateTime &out ) const { out.FromString( m_sValue ); } +bool XNode::GetAttrValue( const CString &sName, CString &out ) const { const CString* pAttr=GetAttr(sName); if(pAttr==NULL) return false; out = *pAttr; return true; } +bool XNode::GetAttrValue( const CString &sName, int &out ) const { const CString* pAttr=GetAttr(sName); if(pAttr==NULL) return false; out = atoi(*pAttr); return true; } +bool XNode::GetAttrValue( const CString &sName, float &out ) const { const CString* pAttr=GetAttr(sName); if(pAttr==NULL) return false; out = strtof(*pAttr, NULL); return true; } +bool XNode::GetAttrValue( const CString &sName, bool &out ) const { const CString* pAttr=GetAttr(sName); if(pAttr==NULL) return false; out = atoi(*pAttr) != 0; return true; } +bool XNode::GetAttrValue( const CString &sName, unsigned &out ) const { const CString* pAttr=GetAttr(sName); if(pAttr==NULL) return false; out = 0; sscanf(*pAttr,"%u",&out); return true; } +bool XNode::GetAttrValue( const CString &sName, DateTime &out ) const { const CString* pAttr=GetAttr(sName); if(pAttr==NULL) return false; out.FromString( *pAttr ); return true; } void XNode::SetValue( int v ) { m_sValue = ssprintf("%d",v); } void XNode::SetValue( float v ) { m_sValue = ssprintf("%f",v); } @@ -556,25 +553,19 @@ void XNode::SetValue( bool v ) { m_sValue = ssprintf("%d",v); } void XNode::SetValue( unsigned v ) { m_sValue = ssprintf("%u",v); } void XNode::SetValue( const DateTime &v ) { m_sValue = v.GetString(); } -const XAttr *XNode::GetAttr( const CString &attrname ) const +const CString *XNode::GetAttr( const CString &attrname ) const { - map::const_iterator it = m_attrs.find( attrname ); + map::const_iterator it = m_attrs.find( attrname ); if( it != m_attrs.end() ) - { - DEBUG_ASSERT( attrname == it->second->m_sName ); - return it->second; - } + return &it->second; return NULL; } -XAttr *XNode::GetAttr( const CString &attrname ) +CString *XNode::GetAttr( const CString &attrname ) { - map::iterator it = m_attrs.find( attrname ); + map::iterator it = m_attrs.find( attrname ); if( it != m_attrs.end() ) - { - DEBUG_ASSERT( attrname == it->second->m_sName ); - return it->second; - } + return &it->second; return NULL; } @@ -633,52 +624,20 @@ bool XNode::RemoveChild( XNode *node ) } -// add attribute -XAttr *XNode::AppendAttr( XAttr *attr ) +// detach attribute +bool XNode::RemoveAttr( const CString &sName ) { - DEBUG_ASSERT( attr->m_sName.size() ); - - /* Hinted insert: optimize for alphabetical inserts, for the copy ctor. */ - m_attrs.insert( m_attrs.end(), make_pair(attr->m_sName,attr) ); - return attr; + return m_attrs.erase(sName) > 0; } -// detach attribute and delete object -bool XNode::RemoveAttr( XAttr *attr ) +void XNode::AppendAttr( const CString &sName, const CString &sValue ) { - FOREACHM( CString, XAttr*, m_attrs, p ) - { - if( p->second == attr ) - { - SAFE_DELETE( p->second ); - m_attrs.erase( p ); - return true; - } - } - return false; -} - -XAttr *XNode::AppendAttr( const CString &sName, const CString &sValue ) -{ - XAttr *pAttr = new XAttr; - pAttr->m_sName = sName; - pAttr->m_sValue = sValue; - return AppendAttr( pAttr ); -} - -XAttr *XNode::AppendAttr( const CString &sName, float value ){ return AppendAttr(sName,ssprintf("%f",value)); } -XAttr *XNode::AppendAttr( const CString &sName, int value ) { return AppendAttr(sName,ssprintf("%d",value)); } -XAttr *XNode::AppendAttr( const CString &sName, unsigned value ) { return AppendAttr(sName,ssprintf("%u",value)); } - -void XNode::SetAttrValue( const CString &sName, const CString &sValue ) -{ - XAttr* pAttr = GetAttr( sName ); - if( pAttr ) - pAttr->m_sValue = sValue; - else - AppendAttr( sName, sValue ); + m_attrs.insert( m_attrs.end(), make_pair(sName,sValue) ); } +void XNode::AppendAttr( const CString &sName, float value ){ AppendAttr(sName,ssprintf("%f",value)); } +void XNode::AppendAttr( const CString &sName, int value ) { AppendAttr(sName,ssprintf("%d",value)); } +void XNode::AppendAttr( const CString &sName, unsigned value ) { AppendAttr(sName,ssprintf("%u",value)); } bool XNode::LoadFromFile( const CString &sFile ) { diff --git a/stepmania/src/XmlFile.h b/stepmania/src/XmlFile.h index ebcf4072ce..24c447431f 100644 --- a/stepmania/src/XmlFile.h +++ b/stepmania/src/XmlFile.h @@ -7,24 +7,22 @@ struct DateTime; class RageFileBasic; -struct XAttr; -typedef map XAttrs; +typedef map XAttrs; struct XNode; typedef multimap XNodes; #define FOREACH_Attr( pNode, Var ) \ - XAttrs::iterator Var##Iter; \ - XAttr *Var = NULL; \ - for( Var##Iter = (pNode)->m_attrs.begin(), Var = Var##Iter->second; \ - Var##Iter != (pNode)->m_attrs.end(); \ - ++Var##Iter, Var = Var##Iter->second ) + XAttrs::iterator Var; \ + CString &Var = NULL; \ + for( Var = (pNode)->m_attrs.begin(); \ + Var != (pNode)->m_attrs.end(); \ + ++Var ) #define FOREACH_CONST_Attr( pNode, Var ) \ - XAttrs::const_iterator Var##Iter; \ - const XAttr *Var = NULL; \ - for( Var##Iter = (pNode)->m_attrs.begin(), Var = Var##Iter->second; \ - Var##Iter != (pNode)->m_attrs.end(); \ - ++Var##Iter, Var = Var##Iter->second ) + XAttrs::const_iterator Var; \ + for( Var = (pNode)->m_attrs.begin(); \ + Var != (pNode)->m_attrs.end(); \ + ++Var ) #define FOREACH_Child( pNode, Var ) \ XNodes::iterator Var##Iter; \ @@ -85,21 +83,6 @@ struct DISP_OPT } }; -// XAttr : Attribute Implementation -struct XAttr -{ - CString m_sName; // a duplicate of the m_sName in the parent's map - CString m_sValue; - void GetValue( CString &out ) const; - void GetValue( int &out ) const; - void GetValue( float &out ) const; - void GetValue( bool &out ) const; - void GetValue( unsigned &out ) const; - void GetValue( DateTime &out ) const; - - bool GetXML( RageFileBasic &f, DISP_OPT *opt ) const; -}; - // XMLNode structure struct XNode { @@ -124,6 +107,7 @@ struct XNode unsigned Load( const CString &sXml, PARSEINFO *pi, unsigned iOffset = 0 ); unsigned LoadAttributes( const CString &sAttrs, PARSEINFO *pi, unsigned iOffset ); bool GetXML( RageFileBasic &f, DISP_OPT *opt ) const; + bool GetAttrXML( RageFileBasic &f, DISP_OPT *opt, const CString &sName, const CString &sValue ) const; CString GetXML() const; bool LoadFromFile( const CString &sFile ); @@ -132,14 +116,14 @@ struct XNode bool SaveToFile( RageFileBasic &f, DISP_OPT *opt ) const; // in own attribute list - const XAttr *GetAttr( const CString &sAttrName ) const; - XAttr *GetAttr( const CString &sAttrName ); - bool GetAttrValue( const CString &sName, CString &out ) const { const XAttr* pAttr=GetAttr(sName); if(pAttr==NULL) return false; pAttr->GetValue(out); return true; } - bool GetAttrValue( const CString &sName, int &out ) const { const XAttr* pAttr=GetAttr(sName); if(pAttr==NULL) return false; pAttr->GetValue(out); return true; } - bool GetAttrValue( const CString &sName, float &out ) const { const XAttr* pAttr=GetAttr(sName); if(pAttr==NULL) return false; pAttr->GetValue(out); return true; } - bool GetAttrValue( const CString &sName, bool &out ) const { const XAttr* pAttr=GetAttr(sName); if(pAttr==NULL) return false; pAttr->GetValue(out); return true; } - bool GetAttrValue( const CString &sName, unsigned &out ) const { const XAttr* pAttr=GetAttr(sName); if(pAttr==NULL) return false; pAttr->GetValue(out); return true; } - bool GetAttrValue( const CString &sName, DateTime &out ) const { const XAttr* pAttr=GetAttr(sName); if(pAttr==NULL) return false; pAttr->GetValue(out); return true; } + const CString *GetAttr( const CString &sAttrName ) const; + CString *GetAttr( const CString &sAttrName ); + bool GetAttrValue( const CString &sName, CString &out ) const; + bool GetAttrValue( const CString &sName, int &out ) const; + bool GetAttrValue( const CString &sName, float &out ) const; + bool GetAttrValue( const CString &sName, bool &out ) const; + bool GetAttrValue( const CString &sName, unsigned &out ) const; + bool GetAttrValue( const CString &sName, DateTime &out ) const; // in one level child nodes const XNode *GetChild( const CString &sName ) const; @@ -160,16 +144,12 @@ struct XNode XNode *AppendChild( XNode *node ); bool RemoveChild( XNode *node ); - XAttr *AppendAttr( const CString &sName = CString(), const CString &sValue = CString() ); - XAttr *AppendAttr( const CString &sName, float value ); - XAttr *AppendAttr( const CString &sName, int value ); - XAttr *AppendAttr( const CString &sName, unsigned value ); - XAttr *AppendAttr( const CString &sName, const DateTime &value ); - XAttr *AppendAttr( XAttr *pAttr ); - bool RemoveAttr( XAttr *pAttr ); - - // creates the attribute if it doesn't already exist - void SetAttrValue( const CString &sName, const CString &sValue ); + void AppendAttr( const CString &sName = CString(), const CString &sValue = CString() ); + void AppendAttr( const CString &sName, float value ); + void AppendAttr( const CString &sName, int value ); + void AppendAttr( const CString &sName, unsigned value ); + void AppendAttr( const CString &sName, const DateTime &value ); + bool RemoveAttr( const CString &sName ); XNode() { } XNode( const XNode &cpy );