📄 proj_tree.cpp
字号:
//-----------------------------------------------------------------------------void CCyclicDepends::FindCycles(const TProjects& tree, TDependsCycles* cycles){ cycles->clear(); ITERATE(TProjects, p, tree) { // Look throgh all projects in tree. const CProjKey& project_id = p->first; // If this proj_id was already reported in some cycle, // it's no need to test it again. if ( !IsInAnyCycle(project_id, *cycles) ) { // Analyze for cycles AnalyzeProjItem(project_id, tree, cycles); } }}bool CCyclicDepends::IsInAnyCycle(const CProjKey& proj_id, const TDependsCycles& cycles){ ITERATE(TDependsCycles, p, cycles) { const TDependsChain& cycle = *p; if (find(cycle.begin(), cycle.end(), proj_id) != cycle.end()) return true; } return false;}void CCyclicDepends::AnalyzeProjItem(const CProjKey& proj_id, const TProjects& tree, TDependsCycles* cycles){ TProjects::const_iterator p = tree.find(proj_id); if (p == tree.end()) { LOG_POST( Error << "Unknown project: " << proj_id.Id() ); return; } const CProjItem& project = p->second; // No depends - no cycles if ( project.m_Depends.empty() ) return; TDependsChains chains; ITERATE(list<CProjKey>, n, project.m_Depends) { // Prepare initial state of depends chains // one depend project in each chain const CProjKey& depend_id = *n; if ( !IsInAnyCycle(depend_id, *cycles) ) { TDependsChain one_chain; one_chain.push_back(depend_id); chains.push_back(one_chain); } } // Try to extend this chains TDependsChain cycle_found; bool cycles_found = ExtendChains(proj_id, tree, &chains, &cycle_found); if ( cycles_found ) { // Report chains as a cycles cycles->insert(cycle_found); }}bool CCyclicDepends::ExtendChains(const CProjKey& proj_id, const TProjects& tree, TDependsChains* chains, TDependsChain* cycle_found){ for (TDependsChains::iterator p = chains->begin(); p != chains->end(); ) { // Iterate through all chains TDependsChain& one_chain = *p; // we'll consider last element. const CProjKey& depend_id = one_chain.back(); TProjects::const_iterator n = tree.find(depend_id); if (n == tree.end()) { //LOG_POST( Error << "Unknown project: " << depend_id.Id() ); return false; } const CProjItem& depend_project = n->second; if ( depend_project.m_Depends.empty() ) { // If nobody depends from this project - remove this chain p = chains->erase(p); } else { // We'll create new chains // by adding depend_project dependencies to old_chain TDependsChain old_chain = one_chain; p = chains->erase(p); ITERATE(list<CProjKey>, k, depend_project.m_Depends) { const CProjKey& new_depend_id = *k; // add each new depends to the end of the old_chain. TDependsChain new_chain = old_chain; new_chain.push_back(new_depend_id); p = chains->insert(p, new_chain); ++p; } } } // No chains - no cycles if ( chains->empty() ) return false; // got cycles in chains - we done if ( IsCyclic(proj_id, *chains, cycle_found) ) return true; // otherwise - continue search. return ExtendChains(proj_id, tree, chains, cycle_found);}bool CCyclicDepends::IsCyclic(const CProjKey& proj_id, const TDependsChains& chains, TDependsChain* cycle_found){ // First iteration - we'll try to find project to // consider inside depends chains. If we found - we have a cycle. ITERATE(TDependsChains, p, chains) { const TDependsChain& one_chain = *p; if (find(one_chain.begin(), one_chain.end(), proj_id) != one_chain.end()) { *cycle_found = one_chain; return true; } } // We look into all chais ITERATE(TDependsChains, p, chains) { TDependsChain one_chain = *p; // remember original size of chain size_t orig_size = one_chain.size(); // remove all non-unique elements one_chain.sort(); one_chain.unique(); // if size of the chain is altered - we have a cycle. if (one_chain.size() != orig_size) { *cycle_found = one_chain; return true; } } // Got nothing - no cycles return false;}//-----------------------------------------------------------------------------CProjectTreeFolders::CProjectTreeFolders(const CProjectItemsTree& tree):m_RootParent("/", NULL){ ITERATE(CProjectItemsTree::TProjects, p, tree.m_Projects) { const CProjKey& project_id = p->first; const CProjItem& project = p->second; TPath path; CreatePath(GetApp().GetProjectTreeInfo().m_Src, project.m_SourcesBaseDir, &path); SProjectTreeFolder* folder = FindOrCreateFolder(path); folder->m_Name = path.back(); folder->m_Projects.insert(project_id); }}SProjectTreeFolder* CProjectTreeFolders::CreateFolder(SProjectTreeFolder* parent, const string& folder_name){ m_Folders.push_back(SProjectTreeFolder(folder_name, parent)); SProjectTreeFolder* inserted = &(m_Folders.back()); parent->m_Siblings.insert (SProjectTreeFolder::TSiblings::value_type(folder_name, inserted)); return inserted;}SProjectTreeFolder* CProjectTreeFolders::FindFolder(const TPath& path){ SProjectTreeFolder& folder_i = m_RootParent; ITERATE(TPath, p, path) { const string& node = *p; SProjectTreeFolder::TSiblings::iterator n = folder_i.m_Siblings.find(node); if (n == folder_i.m_Siblings.end()) return NULL; folder_i = *(n->second); } return &folder_i;}SProjectTreeFolder* CProjectTreeFolders::FindOrCreateFolder(const TPath& path){ SProjectTreeFolder* folder_i = &m_RootParent; ITERATE(TPath, p, path) { const string& node = *p; SProjectTreeFolder::TSiblings::iterator n = folder_i->m_Siblings.find(node); if (n == folder_i->m_Siblings.end()) { folder_i = CreateFolder(folder_i, node); } else { folder_i = n->second; } } return folder_i;}void CProjectTreeFolders::CreatePath(const string& root_src_dir, const string& project_base_dir, TPath* path){ path->clear(); string rel_dir = CDirEntry::CreateRelativePath(root_src_dir, project_base_dir); string sep(1, CDirEntry::GetPathSeparator()); NStr::Split(rel_dir, sep, *path);}END_NCBI_SCOPE/* * =========================================================================== * $Log: proj_tree.cpp,v $ * Revision 1000.1 2004/06/01 18:31:29 gouriano * PRODUCTION: UPGRADED [GCC34_MSVC7] Dev-tree R1.3 * * Revision 1.3 2004/05/21 21:41:41 gorelenk * Added PCH ncbi_pch.hpp * * Revision 1.2 2004/05/10 19:50:05 gorelenk * Changed CProjectItemsTree::CreateFrom . * * Revision 1.1 2004/03/02 16:23:57 gorelenk * Initial revision. * * =========================================================================== */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -