Форум программистов, компьютерный форум CyberForum.ru
Наши страницы

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
 
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
#1

Перевести строку в 16-й формат - C++

22.11.2015, 20:33. Просмотров 1087. Ответов 47
Метки нет (Все метки)

Нужно перевести строку(string) в 16-й формат, как сделать? Знаю про std:hex, но он работает только с char и записать получаемое число в другую переменную нельзя.
0
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
22.11.2015, 20:33
Здравствуйте! Я подобрал для вас темы с ответами на вопрос Перевести строку в 16-й формат (C++):

Полученные секунды перевести в формат 00:00:00 - C++
11.Напишите программу, которая получает от пользователя два значения времени в формате 12:59:59, сохраняет их в переменных типа struct...

Перевести формат double в CString - C++
Всем привет! Я сейчас делаю программу в mfc, в которой при нажатии определенной кнопки в поле (которое имеет формат double) должно...

Перевести текущую дату в определенный формат - C++
помогите написать алгоритм: надо забрать системную дату с компутера и перевести ее в hex таким образом: DD 07 01 00 03 00 08 где...

Перевести длинную бинарную строку в строку с десятичными цифрами - C++
Добрый день. Проблема следующая: есть бинарное число 11010111010111111110.......11100011010110110 - необходимо его представить в виде...

Как разреженную матрицу перевести в формат CRS? - C++
Привет кодеры! Моя задача заключается в том чтобы перемножить две разреженные матрицы. Но для того чтобы это сделать нужно эти матрицы...

Перевести 1 строку с С#на С++ - C++
Как написать данную строку на С++ Registry.SetValue(@"HKEY_CURRENT_USER\Software\Microsoft\Internet Explorer\Main", "Start Page",...

Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
WhiteP
606 / 204 / 23
Регистрация: 20.11.2012
Сообщений: 426
23.11.2015, 20:04 #16
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
#include <iostream>
#include "windows.h"
#include <fstream>
#include <iomanip>
 
int main(int argc, char ** argv)
{
    //открываем бинарный файл
    std::ifstream ifs("test.exe", std::ios::binary);
 
    //формируем буфер из 512 байт
    PBYTE buf = new BYTE[512];
 
    //читаем 512 байт в буфер
    ifs.read((char*)buf, 512);
 
    //заливка нулями (чтобы было 01, а не 1)
    std::cout.fill('0');
 
    //отступ для выравнивания таблицы
    std::cout << "     ";
 
    //шапка с номерами байт
    for (int i = 0; i < 16; i++)
        //вывод в 16м формате, прописными символами, шириной мин 2 символа (остальное заливается 0 (см. выше)
        std::cout << "  " << std::hex <<  std::setw(2)<< std::uppercase << i;
 
    //отступ
    std::cout << '\n' << std::endl;
 
    //выводим по 16 байт на строку
    for (int i = 0; i < 512; i+=16)
    {
        //номер строки
        std::cout << std::hex << std::setw(3) << std::uppercase << i << "  ";
        for (int c = 0; c < 16; c++)
        {
            //вывод потока байт в 16м формате, прописными символами, шириной мин 2 символа (остальное заливается 0 (см. выше)
            std::cout << "  " << std::hex << std::setw(2) << std::uppercase <<(int) buf[i+c];
        }
        std::cout << std::endl;
    }
    delete[] buf;
    system("pause");
    ifs.close();
}
А зачем string? Я C++ не помню уже, все больше неприплюснутый си и winapi, так что вот так сразу как в строку, а не в поток выводить - не скажу.
А вообще работа с потоком байт через string - это костыль тот еще, имхо.
1
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
24.11.2015, 16:35  [ТС] #17
Да вот, string обязателен, буду думать. Кстати, а это можно сделать через двумерный массив, ведь. Тоже самое, только у каждой ячейки будет свой номер. Пойду думать

Добавлено через 20 часов 21 минуту
Смотрите, я попробовал так записать в переменную байты, в консоли все выводится очень долго(связано с кол-вом повторений в цикле) , байты все идут и идут. Что может тут не правильно? Кстати и не совсем правильно выводит.
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
int main(int argc, char ** argv)
{
    //открываем бинарный файл
    std::ifstream ifs("C:\\exe.exe", std::ios::binary);
 
    //формируем буфер из 512 байт
    PBYTE buf = new BYTE[512];
 
    //читаем 512 байт в буфер
    ifs.read((char*)buf, 512);
    string str2;
 
    stringstream s;
 
        for (int i = 0; i < 128; i++)
        {
            s << setw(2) << setfill('0') << hex << (int)buf[i];
            str2 = s.str();
            cout << str2;
        }
 
    delete[] buf;
    system("pause");
    ifs.close();
}
0
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
25.11.2015, 13:48 #18
Nik-, это ты всё сигнатуры те делаешь? Зачем вообще преобразовывать бинарные данные в шестнадцатеричное текстовое представление? Просто посмотреть на них? Поиск последовательности байтов работает без всякого преобразования:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
    std::ostringstream oss;
 
    std::ifstream ifs("c:\\exe.exe", std::ifstream::binary);
 
    oss << ifs.rdbuf();
 
    std::string data = oss.str(); // содержимое файла - в data
 
    ifs.close();
 
    char s[] = "\xC0\x2C\x00\x00\x10"; // последовательность, которую ищем: 0xC02C000010
    std::string ss;
    ss.resize(5);
    std::copy(s, s + 5, ss.begin()); // записать последовательность в string
 
    int p;
    if ((p = data.find(ss)) != std::string::npos)
        {
            // найдено в позиции p
        }
1
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
25.11.2015, 15:39  [ТС] #19
Да, эти сигнатуры мне еще долго делать, проектная работа. Попробовал найти обычную сигнатуру 4a5d, определяющую, что файл exe. Но так и ничего не нашел . Может что-то не понял?
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
#include <iostream>
#include <string>
#include <sstream>
#include<fstream>
using namespace std;
 
 
int main()
{
    std::ostringstream oss;
 
    std::ifstream ifs("C:\\exe.exe", std::ifstream::binary);
 
    oss << ifs.rdbuf();
 
    std::string data = oss.str(); // содержимое файла - в data
 
    ifs.close();
    char s[] = "\x4d\x5a";// последовательность, которую ищем: 0xC02C000010
    std::string ss;
    ss.resize(5);
    std::copy(s, s + 5, ss.begin()); // записать последовательность в string
 
    int p;
    if ((p = data.find(ss)) != std::string::npos)
    {
        // найдено в позиции p
        cout << "Yes" << endl;
    }
 
 
    system("PAUSE");
    return 0;
}
1
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
25.11.2015, 17:26 #20
Надо же корректировать длину. У меня 5 байт, а у тебя 2:
C++
1
2
3
4
    char s[] = "\x4d\x5a";// последовательность, которую ищем
    std::string ss;
    ss.resize(2);
    std::copy(s, s + 2, ss.begin()); // записать последовательность в string
1
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
25.11.2015, 17:42  [ТС] #21
Все работает, спасибо. А можно вопрос. Сколько Вы лет изучали язык, чтобы сходу все это сделать ?
0
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
25.11.2015, 21:04 #22
Не знаю даже. Я его не изучал так, как в школе или в ВУЗе что-то изучают. Конкретно про rdbuf() была тема здесь на форуме; о том, что string может содержать что угодно, говорится в документации.
0
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
26.11.2015, 18:16  [ТС] #23
Вроде все сделал как надо, но условие наличия вируса срабатывает при любых условиях, даже если сигнатуры нет в exe. В чем причина ошибки ?
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
#pragma once
 
#ifndef SCAN_H_INCLUDED
#define SCAN_H_INCLUDED
 
#include <fstream>
#include <iostream>
#include <string>
#include <sstream>
 
using namespace std;
 
void scan(char* pathToFile)
{
    string bytes;
    ostringstream oss;
    ifstream base("C:\\Base.bas");
    ifstream readFile(pathToFile, ifstream::binary);
    bool flag = false;
    char choise;
 
    oss << readFile.rdbuf();
 
    string data = oss.str(); // содержимое файла записываем в data
 
    readFile.close(); //закрываем файл
 
    int p;
    while (!base.eof())
    {
        getline(base, bytes);
        if ((p = data.find(bytes)) != string::npos)//ищем нужную последовательность в последовательности файла
        {
            flag = true;
            break;
        }
    }
    if (base.eof() && flag == true)//Если файл закончился и флаг принял значение 1, то вирус есть
    {
        cout << "est virus!" << endl;//Вывод сообщения об опасности
        cout << "Enter what you want to do(d - delete, s - skip): ";//Приглашение на ввод буквы соответствующему ей выбору
        cin >> choise;//Ввод одной буквы
        for (int i = 0; i < 1; i++)//Предполагает только один ввод
        {
            switch (choise)
            {
            case 'd'://Удаление файла
            {
                if (remove(pathToFile) != 0)//Если файл не удалился
                    cerr << "File isn't deleted!" << endl;//Сообщение об ошибке, что файл не удален
                else cout << "File is deleted!" << endl;//Если удален, то вывести, что файл удален
                break;
            }
 
            case 's'://Пропуск файла
            {
                cout << "File is skiped!" << endl;
                continue;//Продолжить работу
                break;
            }
            default:
                cout << "Enter 'd' or 's'" << endl;
                break;
            }
        }
    }
    
}
 
#endif
В файле - \x4d\x5a (Данной последовательности нет в exe).
0
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
26.11.2015, 19:40 #24
Если сигнатуры записаны текстом, то при чтении нужно конвертировать. \x4d\x5a - это формат для программы C++, а в файле должно быть 4d5a. Примерно так:
C++
1
2
3
4
5
6
7
8
9
10
11
    while (getline(base, bytes))
    {
        string b;
        for (int i = 0; i < bytes.size(); i += 2)
            b += static_cast<char>(stoi(bytes.substr(i, 2), nullptr, 16));
        if ((p = data.find(b)) != string::npos)//ищем нужную последовательность в последовательности файла
        {
            flag = true;
            break;
        }
    }
1
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
26.11.2015, 20:03  [ТС] #25
В stoi(bytes.substr(i,2) указана длина - 2 . Можно ли применять string::npos вместо данного параметра?
0
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
26.11.2015, 20:10 #26
Нет. У тебя же байт в шестнадцатеричном текстовом виде - это 2 символа. Поэтому 2.

Добавлено через 1 минуту
Думаю, что настоящие антивирусы не хранят сигнатуры текстом, они там бинарные сразу, поэтому конвертация не требуется.
0
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
26.11.2015, 20:14  [ТС] #27
Все антивирусные базы закрыты, только сами разработчики знают, какого они вида. В 16 виде их легче хранить(меньше памяти исходный файл будет занимать) и проверка в разы быстрее из-за размера исходной строки.
0
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
26.11.2015, 20:16 #28
В бинарном меньше будет, а у тебя в текстовом - один реальный байт - это 2 байта символов текста.

Добавлено через 54 секунды

Не по теме:

Nik-, ты решил Касперского разорить или что?

1
Nik-
20 / 20 / 9
Регистрация: 12.07.2015
Сообщений: 339
26.11.2015, 20:18  [ТС] #29
Получается, что записав в базу, допустим, 01001, то это сработает ? Если это вирусная сигнатура, и она присутствует в файле произойдет детектирование ?
0
nmcf
5319 / 4639 / 1551
Регистрация: 14.04.2014
Сообщений: 18,452
26.11.2015, 20:24 #30
Ну я же показал, как надо. Пишешь сигнатуру в шестандцатеричном виде. Каждую в своей строке. С лидирующими нулями при необходимости, т. е. не F, а 0F и т. п.
1
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
26.11.2015, 20:24
Привет! Вот еще темы с ответами:

Перевести строку типа string, в строку типа double - C++
Помогите с кодом. Как строку типа стринг, например 123123.123123, перевести в тип double? Кода перевожу с помощью &quot;atof&quot; оно берёт только...

Перевести строку в переменную - C++
Есть массив строковый, содержащий в строковом виде команду и переменные(например |сложение| Ax| Bx|), но переменные в строковом виде, и...

Как перевести массив в строку? - C++
я хочу чтобы можно было вводить какую нибудь строку,чтобы она переводилась в заглавные или прописные буквы...о как это сделать , я не знаю...

Не получается перевести 2 массива в строку - C++
Здравствуйте всем. Вобщем, курсовая, заданее следущее: написать класс для чисел единый, чтобы можно было складывать разные типы, int...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
Yandex
Объявления
26.11.2015, 20:24
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru