Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > C/C++: Общие вопросы > Как открыть файл(RAR)


Автор: CDell 29.10.2007, 18:30
Вот всё письмо отправляю smile 
С письмом нужно отправить RAR архив.
Как открыть этот RAR архив и запихнуть в строчку, для того чтобы кодировать её в Base64?

Автор: JackYF 29.10.2007, 19:04
Цитата(CDell @  29.10.2007,  18:30 Найти цитируемый пост)
Как открыть этот RAR архив и запихнуть в строчку

ну как:

fopen, последовательно читаем в буфер, енкодим, записываем в выходной буфер, оттуда в файл.

Автор: CDell 29.10.2007, 20:45
Есть файл text.rar = 72 байт
    
Читаю его:

Код

    FILE * pFile = fopen("text.rar", "r"); 
    char buff[1024]; 
    while(fgets(buff, 1023, pFile) != NULL) 
    { 
    } 
    fclose(pFile); 


В buff на появляется сообщение Rar!

Автор: JackYF 29.10.2007, 21:04
Цитата(CDell @  29.10.2007,  20:45 Найти цитируемый пост)
fgets

fread

Автор: jonie 29.10.2007, 21:26
ябы даже больше сказал
Код

fopen("file.ext", "rb");


и вообще чтение всего файла не требуется : base64 блочный алгоритм....

Автор: CDell 2.11.2007, 19:32
Чёт всёравно не получаеться smile 

Код

FILE *f = fopen("text.rar", "rb");
char *text = new char[400];
fread(text, 100, 1, f);
fclose(f);


На выводе опять ошибку выдаёт что рар архив.

Цитата

и вообще чтение всего файла не требуется : base64 блочный алгоритм.... 

А можно поподробней? Был бы очень рад если бы привёл примерчик. smile 



Автор: jonie 3.11.2007, 08:57
хм... ну давай те поожем )
Код

namespace base64
{
  const char to_table[64] = 
  {
    'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H',
    'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P',
    'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X',
    'Y', 'Z', 'a', 'b', 'c', 'd', 'e', 'f',
    'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n',
    'o', 'p', 'q', 'r', 's', 't', 'u', 'v',
    'w', 'x', 'y', 'z', '0', '1', '2', '3',
    '4', '5', '6', '7', '8', '9', '+', '/'
  };

  const char from_table[128] =
  {
    -1, -1, -1, -1, -1, -1, -1, -1, // 0
    -1, -1, -1, -1, -1, -1, -1, -1, // 8
    -1, -1, -1, -1, -1, -1, -1, -1, // 16
    -1, -1, -1, -1, -1, -1, -1, -1, // 24
    -1, -1, -1, -1, -1, -1, -1, -1, // 32
    -1, -1, -1, 62, -1, -1, -1, 63, // 40
    52, 53, 54, 55, 56, 57, 58, 59, // 48
    60, 61, -1, -1, -1,  0, -1, -1, // 56
    -1,  0,  1,  2,  3,  4,  5,  6, // 64
     7,  8,  9, 10, 11, 12, 13, 14, // 72
    15, 16, 17, 18, 19, 20, 21, 22, // 80
    23, 24, 25, -1, -1, -1, -1, -1, // 88
    -1, 26, 27, 28, 29, 30, 31, 32, // 96
    33, 34, 35, 36, 37, 38, 39, 40, // 104
    41, 42, 43, 44, 45, 46, 47, 48, // 112
    49, 50, 51, -1, -1, -1, -1, -1  // 120
  };

  typedef unsigned char BYTE;
  typedef unsigned short WORD;
  typedef unsigned int  DWORD;
 
  template <class InputIterator, class OutputIterator>
  void encode(const InputIterator& begin, 
              const InputIterator& end, 
              OutputIterator out)
  {
        InputIterator it = begin;
        int lineSize = 0;    //длинна строки
        int n_bytes;        //кол-во байт взятых
        DWORD dwInput;        //для сохранения 3-х байт
        do{
            dwInput = 0;
            //берем три байта
            for(n_bytes = 0; (n_bytes<3)&&(it != end) ; ++n_bytes,++it){
                dwInput <<= 8;
                dwInput += static_cast<BYTE>(*it);
            }

            //кодируем в BASE64
            int n_bits = n_bytes*8;
            while (n_bits > 0){
                n_bits-=6;
                BYTE index = ((n_bits < 0) ? dwInput << -n_bits : dwInput >> n_bits) & 0x3F;
                *out =  to_table[index];
                ++out;
                ++lineSize;
            }
            
            //строка больше или равна 76 симаолам?
            if(lineSize >= 76){
                //*out = 0x0D;
                ++out;
                *out = 0x0A;
                ++out;
                lineSize = 0;
            }

        }while(n_bytes==3);

        //установим последнюю строку, если надо
        if(n_bytes){
            while(n_bytes++<3){
                *out = '=';
                ++out;
            }
        }
  }
}    //end base64 namespace

и используемс это ...
Код

ifstream in("base64.bin",ios::binary);
noskipws(in);
string base64;

base64::encode( istream_iterator<unsigned char>(in),
        istream_iterator<unsigned char>(), 
        back_inserter(base64));

in.close();

Автор: CDell 3.11.2007, 12:17
Спасибо.
Но из-за своих кривых рук немогу собрать это.

Вот что получилось:
Код

#include <iostream>
#include <fstream>
#include <iterator>

//Здесь твой первый кусок кода

int main()
{
    using namespace std;

    ifstream in("base64.bin",ios::binary);
    noskipws(in);
    string base64;

    base64::encode(istream_iterator<unsigned char>(in),
                   istream_iterator<unsigned char>(), 
                   back_inserter(base64));

    in.close();

return 0;
}

Автор: jonie 3.11.2007, 13:36
как минимум #include <string> пропущен.

Автор: xvr 4.11.2007, 10:06
Цитата

В buff на появляется сообщение Rar!

Цитата(CDell @ 2.11.2007,  19:32)
Чёт всёравно не получаеться smile 

Код

FILE *f = fopen("text.rar", "rb");
char *text = new char[400];
fread(text, 100, 1, f);
fclose(f);


На выводе опять ошибку выдаёт что рар архив.

Цитата

и вообще чтение всего файла не требуется : base64 блочный алгоритм.... 

А можно поподробней? Был бы очень рад если бы привёл примерчик. smile

Rar! - это не ошибка, это первые 4 символа в любом RAR архиве.

Автор: CDell 4.11.2007, 22:01
Цитата

как минимум #include <string> пропущен. 

Всёравно ошика вылетает на то что в этом файле #include <iterator>

Автор: JackYF 4.11.2007, 22:02
CDell, какой компилятор/среда программирования?

Автор: CDell 4.11.2007, 23:25
Цитата

CDell, какой компилятор/среда программирования? 

Microsoft Visual C++ 6.0

Ошибка вот:
Код

c:\program files\microsoft visual studio\vc98\include\iterator(82) : error C2039: 'push_back' : is not a member of 'basic_string<char,struct std::char_traits<char>,class std::allocator<char> >'
        c:\program files\microsoft visual studio\vc98\include\iterator(82) : while compiling class-template member function 'class std::back_insert_iterator<class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > > &_
_thiscall std::back_insert_iterator<class std::basic_string<char,struct std::char_traits<char>,class std::allocator<char> > >::operator =(const char &)'
Error executing cl.exe.


Это если подключаем #include <iterator>, а если без него
Код

c:\cpp\zen\zen.cpp(104) : error C2065: 'istream_iterator' : undeclared identifier
c:\cpp\zen\zen.cpp(104) : error C2062: type 'unsigned char' unexpected
Error executing cl.exe.

Автор: JackYF 5.11.2007, 02:33
Ага... пробуй

вместо
Цитата(CDell @  3.11.2007,  12:17 Найти цитируемый пост)
string base64;

Код

basic_string<unsigned char> base64;


#include <iterator> надо.

Автор: CDell 5.11.2007, 17:28
Всёравно ошибка таже.

Автор: JackYF 5.11.2007, 17:39
Цитата(CDell @  4.11.2007,  23:25 Найти цитируемый пост)
Microsoft Visual C++ 6.0

Меняй компилятор на более нормальный.

Цитата(CDell @  4.11.2007,  23:25 Найти цитируемый пост)
'push_back' : is not a member of 'basic_string<char,struct std::char_traits<char>,class std::allocator<char> >'

по стандарту эта функция должна быть у basic_string<T>. Так что незачёт той реализации STL, которая поставляется с этим компилятором.

Автор: CDell 5.11.2007, 21:31
Ага. Спасибо.
Microsoft Visual Studio 2005 проглотил smile 
Теперь вопрос в том кудаже помещается  результат? Как его вывести, а точненее что выводить?

Автор: jonie 5.11.2007, 22:15
в base64 у тебя будет base64-закодированные данные (всего файла, т.е. расчитывай что будет это в памяти весить больше чем исходный файл)
cout<<base64;

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)