Как я преобразовываю jstring в wchar_t *

50! - 30414093201713378043612608166064768844377641568960512000000000000 или около 3.04e+64, 215-битное число. Это значение обычно превышает диапазон типов, например long. Даже uintmax_t и unsigned long long необходимо только иметь возможность представлять по меньшей мере 64-битные целые числа.

long int fact(long int n) {
  ...
  // Overflows!
  return n*fact(n-1);

Чтобы получить точный ответ, код может использовать альтернативные типы. Следующее использует строковое / десятичное представление целого числа. Он работает при больших значениях n, так как правильная функциональность ограничена размером буфера.

char *strfact_mult(char *s, unsigned x) {
  unsigned sum = 0;
  size_t len = strlen(s);
  size_t i = len;
  while (i > 0) {
    sum += (s[--i] - '0')*x;
    s[i] = sum%10 + '0';
    sum /= 10;
  }
  while (sum) {
    len++;
    memmove(&s[1], s, len);
    s[i] = sum%10 + '0';
    sum /= 10;
  }
  return s;
}

char *str_fact(char *dest, unsigned n) {
  strcpy(dest, "1");
  while (n > 1) {
    strfact_mult(dest, n--);
  }
  return dest;
}

int main(void) {
  char buf[1000];
  puts(str_fact(buf, 0));
  puts(str_fact(buf, 1));
  puts(str_fact(buf, 5));
  puts(str_fact(buf, 50));
}

Выход

1
1
120
30414093201713378043612608166064768844377641568960512000000000000
12
задан piyushj 13 July 2016 в 12:28
поделиться

6 ответов

JNI имеет GetStringChars () функция также. Тип возврата является константой jchar*, jchar является 16-разрядным на win32 настолько способом, который был бы совместим с wchar_t. Не уверенный, если это - реальный UTF-16 или что-то еще...

3
ответ дан 2 December 2019 в 06:10
поделиться

Портативное и надежное решение состоит в том, чтобы использовать iconv с пониманием, что необходимо знать что кодирование системы wchar_t использование (UTF-16 в Windows, UTF-32 во многих системах Unix, например).

Если Вы хотите минимизировать свою зависимость от стороннего кода, Вы можете также ручная самокрутка UTF-8 Ваш собственный преобразователь. Это легко при преобразовании в UTF-32, несколько тяжелее с UTF-16, потому что необходимо обработать суррогатные пары также.:-P Кроме того, необходимо стараться отклонить несамые короткие формы, или это может открыть ошибки безопасности в некоторых случаях.

3
ответ дан 2 December 2019 в 06:10
поделиться

Если мы не интересуемся кросс-платформенной способностью, окнами можно использовать функцию MultiByteToWideChar или полезные макросы A2W (касательно примера).

0
ответ дан 2 December 2019 в 06:10
поделиться

Просто используйте env-> GetStringChars (myString, 0); Java передает Unicode по своей природе

0
ответ дан 2 December 2019 в 06:10
поделиться

Я знаю, что этот вопрос был задан год назад, но мне не нравятся другие ответы, поэтому я все равно отвечу. Вот как мы это делаем в нашем источнике:

wchar_t * JavaToWSZ(JNIEnv* env, jstring string)
{
    if (string == NULL)
        return NULL;
    int len = env->GetStringLength(string);
    const jchar* raw = env->GetStringChars(string, NULL);
    if (raw == NULL)
        return NULL;

    wchar_t* wsz = new wchar_t[len+1];
    memcpy(wsz, raw, len*2);
    wsz[len] = 0;

    env->ReleaseStringChars(string, raw);

    return wsz;
}

РЕДАКТИРОВАТЬ : Это решение хорошо работает на платформах, где wchar_t составляет 2 байта, некоторые платформы имеют 4 байта wchar_t, и в этом случае это решение не будет работать.

2
ответ дан 2 December 2019 в 06:10
поделиться

А кто освобождает wsz? Я бы рекомендовал STL!

std::wstring JavaToWSZ(JNIEnv* env, jstring string)
{
    std::wstring value;
    if (string == NULL) {
        return value; // empty string
    }
    const jchar* raw = env->GetStringChars(string, NULL);
    if (raw != NULL) {
        jsize len = env->GetStringLength(string);
        value.assign(raw, len);
        env->ReleaseStringChars(string, raw);
    }
    return value;
}
4
ответ дан 2 December 2019 в 06:10
поделиться
Другие вопросы по тегам:

Похожие вопросы: