부끄럽지만 거의 배꼈습니다. ㅡ.ㅡ

일단 간단하게 zip파일(여러 파일이 압축된것) 압축을 풀수 있습니다.
단순버전
// 압축 파일을 해제 한다.
bool ExtractZip( const string & zipFile, const string & dstPath )
{
    // Zip파일 오픈
    unzFile uf = unzOpen( zipFile.c_str() );

    // 첫번째 Zip목록으로 이동
    int ret = unzGoToFirstFile(uf);

    for(;;)
        {
                unz_file_info   file_info;

                // 압축된 파일명을 얻음.
                char fileName[MAX_PATH];
                ret = unzGetCurrentFileInfo( uf, &file_info, fileName, sizeof(fileName), NULL, 0, NULL, 0 );

                // 압축된 파일 하나를 연다.
                ret = unzOpenCurrentFile( uf );

                // 폴더 만들기.
                MkPath( targetFilename );

                // 파일로 쓰기.
                ofstream    ofs( targetFilename.c_str() );

                // 압축을 푼다.
                char buf[4096];
                for(;;)
                {
                        int len = unzReadCurrentFile( uf, buf, sizeof(buf) );
                        if( len == 0 )
                                break;
                        ofs.write( buf, len );
                }
                ofs.close();

                unzCloseCurrentFile( uf );

                ret = unzGoToNextFile( uf );
        }

        if(ret==UNZ_END_OF_LIST_OF_FILE)
                break;

        unzCloseCurrentFile(uf);

        unzClose(uf);

    return true;
}


전체버전
// 작성자 : fehead.tistory.com
//
// 사용법 : lunzip.exe 압축파일 압축풀디렉토리
//    예제) lunzip.exe c:\test.zip c:\tmp\test
//
// 빌드 환경 : visual c++ 2003, 2008
//
// 참고자료 : zipj03.7z http://www.kippler.com/win/zipj/
//            minizip http://www.winimage.com/zLibDll/minizip.html

#include < iostream >
#include < string >
#include < Windows.h >
#include < direct.h >
#include < fstream >
#include "unzip/unzip.h"

using namespace std;

bool ExtractZip( const string & zipFile, const string & dstPath );  // 압축파일을 해당 디렉토리에 푼다.
bool IsDirectory( const string & path );                            // 디렉토리인지 확인
bool MkPath( const string & fullPath );                             // 해당 디렉토리를 만듬.

// 메인 함수
int main( int argc, char * argv[] )
{
    if( argc != 3 )
    {
        cout << "사용법 : lunzip.exe 압축파일 압축풀디렉토리\n";
        return 0;
    }

    ExtractZip( argv[1], argv[2] );

    //ExtractZip( "d:\\test.zip", "d:\\tmp\\test" );
    return 0;
}

// 디렉토리인지 알아냄.
bool IsDirectory( const string & path )
{
    DWORD ret = GetFileAttributes( path.c_str() );
    
    if( ret == 0xffffffff)
        return false;

    if( ret & FILE_ATTRIBUTE_DIRECTORY )
        return true;

    return false;
}

// 디렉토리를 만든다.
bool MkPath( const string & fullPath )
{
    string  path = fullPath;

    // 파일경로에서 디렉토리 경로만 얻음.
    string::size_type pos = path.find_last_of( "/\\" );
    if( pos != string::npos )
    {
        path.erase( ++pos, string::npos );
    }

    // 네트워크 경로 인가? 예제) "\\192.168.0.1\test"
    pos = 0;
    if( path.compare( 0, 2, "\\\\") == 0 )
        pos = 2;

    // 상위 경로를 찾아가며 디렉토리를 순서대로 만든다.
    while( (pos = path.find_first_of( "/\\", pos )) != string::npos )
    {
        string subPath = path.substr( 0, pos++ );
        
        if(IsDirectory( subPath )==false)
            _mkdir( subPath.c_str() );
    }

    return IsDirectory( fullPath );
}

// 압축 파일을 해제 한다.
bool ExtractZip( const string & zipFile, const string & dstPath )
{
    // Zip파일 오픈
    unzFile uf = unzOpen( zipFile.c_str() );
    if( uf == 0 )
        return false;

    // 첫번째 Zip목록으로 이동
    int ret = unzGoToFirstFile(uf);

    if( ret != UNZ_OK )
        goto END;

    for(;;)
    {
        unz_file_info   file_info;
        
        // 압축된 파일명을 얻음.
        char fileName[MAX_PATH];
        ret = unzGetCurrentFileInfo( uf, &file_info, fileName, sizeof(fileName), NULL, 0, NULL, 0 );

        if( ret != UNZ_OK )
            goto END;

        // 압축된 파일 하나를 연다.
        ret = unzOpenCurrentFile( uf );
        if ( ret != UNZ_OK )
        {
            cerr << fileName << " 파일 열기 실패\n";
            break;
        }

        // TargetFilename = destPath + "\\" + "압축 풀려는 파일명"
        string targetFilename = dstPath;
        if( *targetFilename.rbegin()  != '\\' )
            targetFilename.append( "\\" );
        targetFilename.append( fileName );

        // 폴더 만들기.
        MkPath( targetFilename );

        if( IsDirectory( targetFilename ) == false )
        {
            // 파일로 쓰기.
            ofstream    ofs( targetFilename.c_str() );
            if( !ofs )
            {
                cerr << "파일 열기 실패:" << targetFilename << endl;
                break;
            }
            cout << targetFilename << " : " << file_info.uncompressed_size << "bytes\n";

            // 압축을 푼다.
            char buf[4096];
            for(;;)
            {
                int len = unzReadCurrentFile( uf, buf, sizeof(buf) );
                if( len < 0 )  
                    goto END;
                if( len == 0 )
                    break;

                ofs.write( buf, len );
            }
            ofs.close();
        }

        unzCloseCurrentFile( uf );

        ret = unzGoToNextFile( uf );

        if(ret==UNZ_END_OF_LIST_OF_FILE)
            break;
    }

END:
    if(uf)
        unzCloseCurrentFile(uf);

    if(uf)
        unzClose(uf);

    return true;
}



참고사이트
  zipj 0.3
  minizip

소스 및 실행파일
 Visual C++ 2003, 2008환경에서 개발하였습니다.
 Visual C++ 2003에서는 디버그 모드에서만 작동하더군요.( std::string 문제 발생 )





+ Recent posts