一种新的用于表示二进制数据 base94 到可打印字符 on C++ 实现。

例子:

        Byte buff[] = "\x5c\x5d";
        int encode_length = 0;
        int decode_length = 0;

        auto encode = ppp::cryptography::ssea::base94_encode(buff, sizeof(buff), encode_length);

        auto decode = ppp::cryptography::ssea::base94_decode(encode.get(), encode_length, decode_length);

头文件:

        class ssea
        {
        public:
            static std::shared_ptr    base94_encode(const void* data, int datalen, int& outlen) noexcept;
            static std::shared_ptr    base94_decode(const void* data, int datalen, int& outlen) noexcept;
        };

源代码:

        std::shared_ptr ssea::base94_encode(const void* data, int datalen, int& outlen) noexcept
        {
            static constexpr int BASE94_RADIX = 94;
            static constexpr int BASE93_RADIX = 93;

            Byte* bytes = (Byte*)data;
            outlen = 0;

            if (NULL == data || datalen < 1)
            {
                return NULL;
            }

            int bucket_length = 0;
            for (int i = 0; i < datalen; i++)
            {
                if (bytes[i] >= BASE93_RADIX)
                {
                    bucket_length += 2;
                }
                else
                {
                    bucket_length++;
                }
            }

            std::shared_ptr bucket_managed = make_shared_alloc(bucket_length);
            if (bucket_managed)
            {
                Byte* bucket = bucket_managed.get();
                for (int i = 0; i < datalen; i++)
                {
                    Byte b = bytes[i];
                    if (b >= BASE93_RADIX)
                    {
                        *bucket++ = '\x20' + (((b / BASE93_RADIX) - 1) + BASE93_RADIX);
                        *bucket++ = '\x20' + (b % BASE93_RADIX);
                    }
                    else
                    {
                        *bucket++ = '\x20' + b;
                    }
                }

                outlen = bucket_length;
            }
            return bucket_managed;
        }

        std::shared_ptr ssea::base94_decode(const void* data, int datalen, int& outlen) noexcept
        {
            static constexpr int BASE94_RADIX = 94;
            static constexpr int BASE93_RADIX = 93;

            Byte* bytes = (Byte*)data;
            outlen = 0;

            if (NULL == data || datalen < 1)
            {
                return NULL;
            }

            int bucket_length = datalen;
            for (int i = 0; i < datalen; i++)
            {
                Byte b = bytes[i];
                if (b < '\x20')
                {
                    return NULL;
                }

                b -= '\x20';
                if (b > BASE94_RADIX)
                {
                    return NULL;
                }

                if (b >= BASE93_RADIX)
                {
                    if (++i < datalen)
                    {
                        b = bytes[i];
                        if (b < '\x20')
                        {
                            return NULL;
                        }

                        b -= '\x20';
                        if (b > BASE93_RADIX)
                        {
                            return NULL;
                        }
                    }
                    else
                    {
                        return NULL;
                    }

                    bucket_length--;
                }
            }

            std::shared_ptr bucket_managed = make_shared_alloc(bucket_length);
            if (bucket_managed)
            {
                Byte* bucket = bucket_managed.get();
                for (int i = 0; i < datalen; i++)
                {
                    Byte b = bytes[i] - '\x20';
                    if (b >= BASE93_RADIX)
                    {
                        int v = (((b - BASE93_RADIX) + 1) * BASE93_RADIX) + (bytes[++i] - '\x20');
                        if (v > 0xff)
                        {
                            return NULL;
                        }

                        *bucket++ = v;
                    }
                    else
                    {
                        *bucket++ = b;
                    }
                }

                outlen = bucket_length;
            }
            return bucket_managed;
        }

你可能感兴趣的:(C/C++,c++,数学建模,算法)