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

📄 publicfunction.cpp

📁 多线程下载的
💻 CPP
📖 第 1 页 / 共 3 页
字号:
// PublicFunction.cpp: implementation of the CPublicFunction class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "NetDownMTR.h"
#include "PublicFunction.h"
#include <Afxmt.h>
#include  <io.h>
#include <direct.h>
#include "log.h"
// for function StrTrim()
#include "Shlwapi.h"
#pragma comment ( lib, "Shlwapi.lib" )

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

const char f_seps[]   = ";";

void DeleteStrAry(CStringArray **ppStrAry)
{
	if ( ppStrAry && (*ppStrAry) )
	{
		(*ppStrAry)->RemoveAll();
		(*ppStrAry)->FreeExtra();
		delete (*ppStrAry);
		(*ppStrAry) = NULL;
	}
}
int PartStringAndAddToStrAry ( char *pStr, CStringArray &StrAry, char *seps/*="\t\r\n"*/ )
{
	StrAry.RemoveAll();
	char *token;
	token = strtok( pStr, seps );
	while( token != NULL )
	{
		/* While there are tokens in "string" */
		StrAry.Add ( token );
		/* Get next token: */
		token = strtok( NULL, seps );
	}
	return StrAry.GetSize();
}

int PartStringAndAddToStrAry ( char *pStr, CStringArray &StrAry, char nPartFlag )
{
	char *pStart = pStr;
	char *pFind = NULL;
	char szTempBuf[10240] = {0};
	LPCTSTR pszTrimChars = "\r\n\t";
	while ( pFind = strchr ( pStart, nPartFlag ) )
	{
		int nLen = pFind - pStart;
		if ( nLen > 0 )
		{
			if ( nLen > sizeof(szTempBuf)-2 )
				nLen = sizeof(szTempBuf)-2;
			memcpy ( szTempBuf, pStart, nLen );
			szTempBuf [ nLen ] = '\0';
			StrTrim ( szTempBuf, pszTrimChars );
			StrAry.Add ( szTempBuf );
		}
		else
		{
			StrAry.Add ( "" );
		}

		pStart = pFind + 1;
	}
	if ( (int)( pStart - pStr ) < (int)strlen ( pStr ) )
		StrAry.Add ( pStart );

	return StrAry.GetSize();
}

int PartStringAndAddToStrAry ( LPCTSTR lpszStr, CStringArray &StrAry, char nFirstFlag, char nSecondFlag )
{
	StrAry.RemoveAll();
	int nStartPos = 0, nEndPos = 0;
	CString csBigString = GET_SAFE_STRING ( lpszStr );
	BOOL bSentence = FALSE;
	for ( ;; )
	{
		char cFindChar = ( bSentence ? nSecondFlag : nFirstFlag );
		int nFindPos = csBigString.Find ( cFindChar, nEndPos );
		if ( nFindPos < 0 )
		{
			if ( bSentence )
			{
				CString csTemp = csBigString.Mid ( nStartPos+1 );
				if ( csTemp.GetLength() > 0 )
					StrAry.Add ( csTemp );
			}
			break;
		}
		if ( !bSentence )
		{
			nStartPos = nFindPos;
			bSentence = TRUE;
		}
		else
		{
			nEndPos = nFindPos;
			CString csTemp = csBigString.Mid ( nStartPos+1, nEndPos-nStartPos-1 );
			StrAry.Add ( csTemp );
			bSentence = FALSE;
		}
		nEndPos = nFindPos + 1;
	}

	return StrAry.GetSize();
}

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
CHwDir::CHwDir(
		LPCTSTR lpszBasePathOrFile,
		BOOL bSerachSubDir/* = TRUE*/,		// 搜索子目录
		BOOL bAbsolutePath /*=TRUE*/,		// 是绝对路径
		CHwDir **ppHwDir/*=NULL*/			// 将这个类的指针传出去给调用者
	)
{
	m_bCancel = FALSE;
	if ( ppHwDir ) *ppHwDir = this;
	m_pStrAryResFile = new CStringArray;
	if ( !m_pStrAryResFile ) return;
	m_pStrArySubDirectory_Private = new CStringArray;
	if ( !m_pStrArySubDirectory_Private ) return;
	m_pStrArySubDirectory = new CStringArray;
	if ( !m_pStrArySubDirectory ) return;

	//初始化变量
	char buf[MAX_PATH];
	m_bSerachSubDir = bSerachSubDir;
	m_bAbsolutePath = bAbsolutePath;
	m_pStrAryResFile->FreeExtra();
	m_pStrArySubDirectory_Private->FreeExtra();
	m_pStrArySubDirectory->FreeExtra();
	m_dwRelativePathStartPos = 0;
	ZeroMemory(m_szBasePathFile,sizeof(m_szBasePathFile));
	int iLen = 0;
	char *p = NULL;
	ZeroMemory(m_strFilter,sizeof(m_strFilter));
	m_AmountBytes = 0;
	iLen = hwSnprintf((char*)m_szBasePathFile,sizeof(m_szBasePathFile)-2,"%s",lpszBasePathOrFile);


	//查找的是目录还是文件,取得目录名和过滤字符(*.*、*.exe、??.cpp等都是过滤条件)
	char TempBuf[MAX_PATH];
	ZeroMemory(TempBuf,sizeof(TempBuf));
	DWORD dwFileAttrib = GetFileAttributes(m_szBasePathFile);
	if((dwFileAttrib & FILE_ATTRIBUTE_DIRECTORY) && dwFileAttrib != 0xffffffff)	//指定搜索一个目录,没有过滤条件
	{
		strcpy(m_strFilter,"*.*");
		if(m_szBasePathFile[iLen - 1] != '\\')
			m_szBasePathFile[iLen] = '\\';
	}
	else	//指定了过滤条件
	{
		PartFileAndPathByFullPath(m_szBasePathFile,m_strFilter,sizeof(m_strFilter),TempBuf,sizeof(TempBuf));
		STRNCPY_SZ( m_szBasePathFile, TempBuf );
	}
	//找相对路径的位置
	if ( !bAbsolutePath )
	{
		strcpy((char*)buf,(const char*)m_szBasePathFile);
		if ( strchr((const char*)buf,':') && strlen((const char*)buf) == 3 )	//是诸如“E:\”、“d:\”的路径
		{
			m_dwRelativePathStartPos = 3;
		}
		else if ( strlen((const char*)buf) == 1 && buf[0] == '\\')			//是“\”,表示搜索当前盘的根目录
		{
			m_dwRelativePathStartPos = 1;
		}
		else																//一般目录(绝对路径、相对路径)
		{
			iLen = (int)strlen((const char*)buf);
			buf[iLen - 1] = '\0';
			p = strrchr((const char*)buf,'\\');
			if(p)
			{
				m_dwRelativePathStartPos = (DWORD)(p - buf + 1);
			}
		}
	}
	Dir();
}

CHwDir::~CHwDir()
{
	DeleteStrAry ( &m_pStrAryResFile );
	DeleteStrAry ( &m_pStrArySubDirectory_Private );
	DeleteStrAry ( &m_pStrArySubDirectory );
}
/********************************************************************************
* Function Type	:	private
* Parameter		:	None
* Return Value	:	获得的文件总数
* Description	:	将目录m_szBasePathFile下的所有文件列举出来
*********************************************************************************/
DWORD CHwDir::Dir()
{
	char strDirectory[MAX_PATH*4];
	DWORD dwLine = 0;
	FindDirAndFile(m_szBasePathFile);
	while(1)
	{
		dwLine = (DWORD)m_pStrArySubDirectory_Private->GetSize();
		if(dwLine < 1) break;
		//处理m_StrArySubDirectory中最后一个子目录
		hwSnprintf((char*)strDirectory,sizeof(strDirectory) - 1,"%s",m_pStrArySubDirectory_Private->GetAt(dwLine - 1));
		m_pStrArySubDirectory_Private->RemoveAt(dwLine - 1);
		FindDirAndFile(strDirectory);
		if ( m_bCancel ) break;
	}
	return m_pStrAryResFile->GetSize();
}
/********************************************************************************
* Function Type	:	private
* Parameter		:	lpszDirectory		-	要搜索的纯目录
* Return Value	:	获得的文件总数
* Description	:	所有一个目录下的所有目录和符合过滤条件的文件
*********************************************************************************/
DWORD CHwDir::FindDirAndFile(LPCTSTR lpszDirectory)
{
	DWORD dwRet = 0;
	char strDirFile[MAX_PATH*2];
	hwSnprintf((char*)strDirFile,sizeof(strDirFile) - 1,"%s*.*",lpszDirectory);				//先搜索出子目录
	dwRet += FindAllFileUnderOneDir((LPCTSTR)strDirFile,lpszDirectory,TRUE);
	hwSnprintf((char*)strDirFile,sizeof(strDirFile) - 1,"%s%s",lpszDirectory,m_strFilter);	//再按过滤条件搜索
	dwRet += FindAllFileUnderOneDir(strDirFile,lpszDirectory,FALSE);
	return dwRet;
}
/********************************************************************************
* Function Type	:	private
* Parameter		:	lpszFileName		-	要处理的文件(这里把目录也视为文件)
*					lpszDirectory		-	纯目录(不需要再找目录了,减少计算量)
*					bFindDir			-	是否只搜索目录,不理会文件
* Return Value	:	获得的文件总数
* Description	:	查找lpszFileName指定的所有文件或所有目录
*********************************************************************************/
DWORD CHwDir::FindAllFileUnderOneDir(LPCTSTR lpszFileName,LPCTSTR lpszDirectory,BOOL bFindDir)
{
	DWORD dwFileNum = 0, dwDirNum = 0;
	WIN32_FIND_DATA FindData;
	HANDLE hFileHandle = FindFirstFile(lpszFileName,&FindData);
	if(hFileHandle == INVALID_HANDLE_VALUE)
		return dwFileNum;
	int iRet = HandleOneFile ( lpszDirectory, &FindData, bFindDir );
	if(iRet == 1)	//是文件
		dwFileNum ++;
	else if(iRet == 2)	//是目录
		dwDirNum ++;
	while ( FindNextFile ( hFileHandle, &FindData ) )
	{
		iRet = HandleOneFile ( lpszDirectory, &FindData, bFindDir );
		if(iRet == 1)	//是文件
			dwFileNum ++;
		else if(iRet == 2)	//是目录
			dwDirNum ++;
		if ( m_bCancel ) break;
	}
	FindClose(hFileHandle);
	return dwFileNum;
}
/********************************************************************************
* Function Type	:	private
* Parameter		:	lpszDirectory		-	纯路径(不包含文件名)
*					pFindData			-	文件信息
*					bFindDir			-	TRUE  : 只搜索目录,不理会文件
*											FALSE : 只搜索文件,不理会目录
* Return Value	:	1					-	是一个有效的文件
*					2					-	是一个有效的目录
*					-1				_	-	不是想要的文件或目录
* Description	:	处理一个找到的文件(这里把目录也视为文件)
*********************************************************************************/
int CHwDir::HandleOneFile(LPCTSTR lpszDirectory, WIN32_FIND_DATA* pFindData,BOOL bFindDir)
{
	char ResBuf[3*MAX_PATH];
	ULONGLONG FileSize;
	LPDWORD pDword = (LPDWORD)&FileSize;
	pDword[0] = pFindData->nFileSizeLow;
	pDword[1] = pFindData->nFileSizeHigh;
	ZeroMemory(ResBuf,sizeof(ResBuf));
	if(stricmp((const char*)pFindData->cFileName,"..")== 0 || pFindData->cFileName[0] == '.')
		return -1;
	if((pFindData->dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) && 
		pFindData->dwFileAttributes != 0xffffffff)
	{
		if(bFindDir)
		{
			if(m_bSerachSubDir)
			{
				hwSnprintf((char*)ResBuf,sizeof(ResBuf) - 1,"%s%s\\",lpszDirectory,pFindData->cFileName);
				m_pStrArySubDirectory_Private->Add((LPCTSTR)ResBuf);
				m_pStrArySubDirectory->Add((LPCTSTR)ResBuf);
				return 2;
			}
		}
	}
	else if(!bFindDir)
	{
		hwSnprintf((char*)ResBuf, sizeof(ResBuf) - 1,
			"%s%s", lpszDirectory+m_dwRelativePathStartPos, pFindData->cFileName );
		m_pStrAryResFile->Add((LPCTSTR)ResBuf);
		m_AmountBytes += FileSize;
#ifdef _DEBUG
		printf("NO.%04d : %s\t\t%d\t字节\n",m_pStrAryResFile->GetSize(),ResBuf,FileSize);
#endif
		return 1;
	}
	return -1;
}

/********************************************************************************
* Function Type	:	public
* Parameter		:	None
* Return Value	:	None
* Description	:	取字节总数
*********************************************************************************/
ULONGLONG CHwDir::GetAmountBytes()
{
	return m_AmountBytes;
}

void CHwDir::Cancel()
{
	m_bCancel = TRUE;
}

//////////////////////////////////////////////////////////////////////
// CHwDirEx Class
//////////////////////////////////////////////////////////////////////

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CHwDirEx::CHwDirEx(
		LPCTSTR lpszMultiFindPath,					// 要搜索的多路径,如“E:\\winnt\\;d:\temp\\;”
		LPCTSTR lpszMultiFindFilter,				// 要搜索的过滤条件,如“*.bmp;*.exe;”
		LPCTSTR lpszMultiExcludeFilter/*=NULL*/,	// 要排除的过滤条件,如“*.bmp;*.exe;”
		BOOL bSerachSubDir/* = TRUE*/,				// 搜索子目录
		BOOL bAbsolutePath /*=TRUE*/,				// 是绝对路径
		CHwDirEx **ppHwDirEx/*=NULL*/				// 将这个类的指针传出去给调用者
)
	: m_AmountBytes ( 0 )
	, m_bCancel ( FALSE )
	, m_pHwDir ( NULL )
{
	ASSERT ( lpszMultiFindPath && strlen(lpszMultiFindPath) > 0 );
	ASSERT ( lpszMultiFindFilter && strlen(lpszMultiFindFilter) > 0 );
	if ( ppHwDirEx ) *ppHwDirEx = this;

	m_pStrAryResFile = new CStringArray;
	if ( !m_pStrAryResFile ) return;
	m_pStrArySubDirectory = new CStringArray;
	if ( !m_pStrArySubDirectory ) return;

	CStringArray StrAryMultiFindPath;
	PartStringAndAddToStrAry ( (char*)lpszMultiFindPath, StrAryMultiFindPath, (char)f_seps[0] );
	for ( int i=0; i<StrAryMultiFindPath.GetSize(); i++ )
	{
		CString csFindPath = StrAryMultiFindPath.GetAt(i);
		DirAll ( csFindPath, lpszMultiFindFilter, lpszMultiExcludeFilter, bSerachSubDir, bAbsolutePath );
		if ( m_bCancel ) break;
	}
}

CHwDirEx::~CHwDirEx()
{
	DeleteStrAry ( &m_pStrAryResFile );
	DeleteStrAry ( &m_pStrArySubDirectory );
}

ULONGLONG CHwDirEx::GetAmountBytes()
{
	return m_AmountBytes;
}

void CHwDirEx::DirAll(
		LPCTSTR lpszFindPath,						// 要搜索的路径,如“E:\\winnt\\”
		LPCTSTR lpszMultiFindFilter,				// 要搜索的过滤条件,如“*.bmp;*.exe;”
		LPCTSTR lpszMultiExcludeFilter/*=NULL*/,	// 要排除的过滤条件,如“*.bmp;*.exe;”
		BOOL bSerachSubDir/* = TRUE*/,				// 搜索子目录
		BOOL bAbsolutePath /*=TRUE*/				// 是绝对路径
)
{
	ASSERT ( lpszFindPath && strlen(lpszFindPath) > 0 );

	CStringArray	StrAryResFile_Find, StrAryResFile_Exclude,
					StrArySubDirectory_Find, StrArySubDirectory_Exclude;
	DWORD			dwAmountBytes_Find = 0, dwAmountBytes_Exclude = 0;

	// 先搜索符合指定过滤条件的文件
	Dir ( lpszFindPath, lpszMultiFindFilter, StrAryResFile_Find, StrArySubDirectory_Find,
		dwAmountBytes_Find,	bSerachSubDir, bAbsolutePath );

	// 再搜索需要排除的文件
	if ( lpszMultiExcludeFilter && strlen ( lpszMultiExcludeFilter ) > 0 )
	{
		ASSERT ( lpszMultiExcludeFilter && strlen(lpszMultiExcludeFilter) > 0 );
		Dir ( lpszFindPath, lpszMultiExcludeFilter, StrAryResFile_Exclude, StrArySubDirectory_Exclude,
			dwAmountBytes_Exclude, bSerachSubDir, bAbsolutePath );
		// 然后从 StrAryResFile_Find 中删除掉需要排除的文件
		for ( int i=0; i<StrAryResFile_Exclude.GetSize(); i++ )
		{
			CString csResFile = StrAryResFile_Exclude.GetAt(i);
			int nFindPos = FindFromArray ( StrAryResFile_Find, csResFile );
			if ( nFindPos >= 0 ) StrAryResFile_Find.RemoveAt ( nFindPos );
			if ( m_bCancel ) break;
		}
	}

	// 最后将搜索结果保存到成员变量中,并清理临时变量
	m_pStrAryResFile->Append ( StrAryResFile_Find );
	m_pStrArySubDirectory->Append ( StrArySubDirectory_Find );
	m_AmountBytes += (dwAmountBytes_Find - dwAmountBytes_Exclude);
	StrAryResFile_Find.RemoveAll();
	StrAryResFile_Exclude.RemoveAll();
	StrArySubDirectory_Find.RemoveAll();
	StrArySubDirectory_Exclude.RemoveAll();
}

void CHwDirEx::Dir(
		LPCTSTR lpszFindPath,						// 要搜索的路径,如“E:\\winnt\\”
		LPCTSTR lpszMultiFindFilter,				// 要搜索的过滤条件,如“*.bmp;*.exe;”
		CStringArray &StrAryResFile,				// 搜索的文件保存到此
		CStringArray &StrArySubDirectory,			// 搜索的子目录保存到此
		DWORD &dwAmountBytes,						// 总字节数保存到此
		BOOL bSerachSubDir/* = TRUE*/,				// 搜索子目录
		BOOL bAbsolutePath /*=TRUE*/				// 是绝对路径
)
{

⌨️ 快捷键说明

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