Pergunta

Estou tentando converter um número inteiro em uma string agora e estou tendo um problema.

Eu recebi o código escrito e trabalhando na maior parte, mas ele tem uma pequena falha ao levar para o próximo lugar. É difícil de descrever, então vou lhe dar um exemplo. Usando a base 26 com um conjunto de caracteres que consiste no alfabeto minúsculo:

0 = "A"
1 = "b"
2 = "C"

...

25 = "Z"
26 = "ba" (isso deve ser igual a "aa")

Parece pular o personagem no local zero no personagem definido em determinadas situações.

O que está me confundindo é que não vejo nada de errado com o meu código. Estou trabalhando nisso há muito tempo e ainda não consigo descobrir.

char* charset = (char*)"abcdefghijklmnopqrstuvwxyz";
int charsetLength = strlen(charset);

unsigned long long num = 5678; // Some random number, it doesn't matter
std::string key

do
{
    unsigned int remainder = (num % charsetLength);
    num /= charsetLength;

    key.insert(key.begin(), charset[remainder]);

} while(num);

Tenho a sensação de que a função está tropeçando no módulo retornando um zero, mas eu tenho trabalhado nisso há tanto tempo, não consigo descobrir como isso está acontecendo. Quaisquer sugestões são bem -vindas.

EDIT: O fato de a string gerada ser pouco Endian é irrelevante para minha aplicação.

Foi útil?

Solução

Se eu entendi corretamente o que você deseja (a numeração usada pelo Excel para colunas, a, b, .. z, aa, ab, ...) Essa é uma notação baseada em representar números a partir de 1. Os 26 dígitos têm valores 1, 2, ... 26 e a base é 26. Portanto, a tem valor 1, valor z 26, valor AA 27 ... Computando essa representação é muito semelhante à repreensão normal que você só precisa ajustar para o deslocamento de 1 em vez de 0.

#include <string>
#include <iostream>
#include <climits>

std::string base26(unsigned long v)
{
    char const digits[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
    size_t const base = sizeof(digits) - 1;
    char result[sizeof(unsigned long)*CHAR_BIT + 1];
    char* current = result + sizeof(result);
    *--current = '\0';

    while (v != 0) {
        v--;
        *--current = digits[v % base];
        v /= base;
    }
    return current;
}

// for testing
#include <cstdlib>

int main(int argc, char* argv[])
{
    for (int i = 1; i < argc; ++i) {
        unsigned long value = std::strtol(argv[i], 0, 0);
        std::cout << value << " = " << base26(value) << '\n';
    }
    return 0;
}

Correndo com 1 2 26 27 52 53 676 677 702 703 Dá

1 = A
2 = B
26 = Z
27 = AA
52 = AZ
53 = BA
676 = YZ
677 = ZA
702 = ZZ
703 = AAA

Outras dicas

Seu problema é que 'a' == 0.

Em outras palavras, 'aa' não é a resposta, porque isso é realmente 00. 'BA' é a resposta correta porque b = '1', o que o torna 10 na base 26, que é 26 em decimal.

Seu código está correto, você parece estar entendendo mal.

Eu acho que você deveria fazer A = 1 e Z = 0 para ter ABC ... Z, como em decimal 1234 ... 90

Compare -o com o sistema decimal: 9 é seguido por 10 e não por 01!

Para obter a solução APROGRAMERS para compilar no meu sistema (estou usando o GCC versão 4.6.1 (Ubuntu/Linaro 4.6.1-9ubuntu3), eu precisava adicionar cabeçalhos;#include <climits> #include<cstdlib>

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top