R декодирует строку из 6-битного двоичного в 8-битный двоичный
Я ищу, чтобы написать эквивалентную функцию R на основе фрагмента C++, который у меня есть. Увидеть ниже:
По сути, я хочу расшифровать это:
I @ `@@ B @@@@@@@@@@@@@@@@@@@ IGZJPCoA @@@@ B @@ | у}wqCLnLp@@@@@@ г @ св @@@ д ^I|VeUt@@@
который был преобразован шесть бит за раз в печатные символы, добавив 0x40 к каждому символу, как сообщение было построено. Приведенный ниже код описывает процесс преобразования печатных значений обратно в двоичный файл. После того, как строки были преобразованы из печатной формы обратно в двоичную, они должны быть переупорядочены с использованием обратного байтового преобразования.
Для того, чтобы:
0010 0100 0000 1000 0000 0000 0000 0000 0010 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000 1001 0001 1101 1010 0010 1001 0000 0000 1110 1111 0000 0100 0000 0000 0000 0000 0000 0010 0000 0000 0000 1111 0011 1001 1111 0111 0111 1100 0100 0011 0011 0010 1110 0011 0011 0000 0000 0000 0000 0000 0000 0000 0000 1110 1000 0000 0100 1111 0110 0000 0100 0000 0000 0000 0000 1100 0101 1110 0010 0111 1100 0101 1010 0101 0101 0111 0100 0000 0000
С R эквивалентом этого:
/*****************************************************************************/
void Binary_Decode_6bit(char *in_string,unsigned char *out_string)
{
int i,j;
/* DECODE string from 6 bit binary to 8 bit binary */
/* Convert each 4 word group into 3 words */
for (i=0, j = 0; i < strlen(in_string); i += 4)
{
out_string[j++] = ((in_string[i] &0x3f) << 2) | ((in_string[i+1] &0x30) >> 4);
out_string[j++] = ((in_string[i+1] &0x0f) << 4) | ((in_string[i+2] &0x3c) >> 2);
out_string[j++] = ((in_string[i+2] &0x03) << 6) | (in_string[i+3] &0x3f);
}
}
/****************************************************************************
Я надеюсь использовать функцию R (или даже RCpp), чтобы применить к довольно большому списку этих сообщений.
Любая помощь приветствуется!
1 ответ
Вы можете использовать ваш C++ (хорошо C) код довольно напрямую из функции, экспортированной в R через Rcpp:
#include <Rcpp.h>
void Binary_Decode_6bit(char *in_string, unsigned char *out_string)
{
int i,j;
/* DECODE string from 6 bit binary to 8 bit binary */
/* Convert each 4 word group into 3 words */
for (i=0, j = 0; i < strlen(in_string); i += 4)
{
out_string[j++] = ((in_string[i] &0x3f) << 2) | ((in_string[i+1] &0x30) >> 4);
out_string[j++] = ((in_string[i+1] &0x0f) << 4) | ((in_string[i+2] &0x3c) >> 2);
out_string[j++] = ((in_string[i+2] &0x03) << 6) | (in_string[i+3] &0x3f);
}
}
// [[Rcpp::export]]
Rcpp::RawVector decode(std::string input) {
if (input.size() % 4 != 0)
Rcpp::stop("input size must be a multiple of 4");
std::vector<unsigned char> tmp(input.size() * 3 / 4);
Binary_Decode_6bit(&input[0], &tmp[0]);
Rcpp::RawVector result(tmp.size());
std::copy(tmp.begin(), tmp.end(), result.begin());
return result;
}
/*** R
decode("I@`@@B@@@@@@@@@@@@@@@@@@@IGZJPCoA@@@@B@@|y}wqCLnLp@@@@@@z@SvA@@@q^I|VeUt@@@@")
decode("I@`@@B@@@@@@@@@@@@@@@@@@@IGZJPCoA@@@@B@@|y}wqCLnLp@@@@@@z@SvA@@@q^I|VeUt@@@")
*/
Выход:
> decode("I@`@@B@@@@@@@@@@@@@@@@@@@IGZJPCoA@@@@B@@|y}wqCLnLp@@@@@@z@SvA@@@q^I|VeUt@@@@")
[1] 24 08 00 00 20 00 00 00 00 00 00 00 00 00 00 00 00 00 00 91 da 29 00 ef 04 00 00 00 20 00 f3 9f 77 c4 33
[36] 2e 33 00 00 00 00 00 e8 04 f6 04 00 00 c5 e2 7c 5a 55 74 00 00 00
> decode("I@`@@B@@@@@@@@@@@@@@@@@@@IGZJPCoA@@@@B@@|y}wqCLnLp@@@@@@z@SvA@@@q^I|VeUt@@@")
Error in decode("I@`@@B@@@@@@@@@@@@@@@@@@@IGZJPCoA@@@@B@@|y}wqCLnLp@@@@@@z@SvA@@@q^I|VeUt@@@") :
input size must be a multiple of 4
Обратите внимание, что я добавил дополнительный, @
в конце входной строки, чтобы получить необходимый размер. Я не сравнивал результаты подробно, но для примера, который я сравнил, ваше двоичное представление идентично моему шестнадцатеричному представлению.