Преобразование size_t в целое число (c ++) - PullRequest
8 голосов
/ 14 января 2011

Я пытался создать цикл for, который будет повторяться в зависимости от длины сетевого пакета. В API существует переменная (size_t) с помощью event.packet-> dataLength. Я хочу выполнить итерацию от 0 до event.packet-> dataLength - 7, увеличивая i на 10 каждый раз, когда выполняется итерация, но у меня возникают проблемы.

Я искал решения, но не смог найти ничего полезного. Я попытался преобразовать size_t в unsigned int и выполнить арифметику с этим, но, к сожалению, это не сработало. В основном все, что я хочу, это:

for (int i = 0; i < event.packet->dataLength - 7; i+=10) { }

Хотя каждый раз, когда я делаю что-то подобное или пытаюсь сделать конверсию, часть i <# огромна. Они дали оператор printf в руководстве для API, который использовал «% u» для печати действительного числа, однако, когда я конвертирую его в беззнаковое целое, оно все равно неверно. Я не уверен, куда идти отсюда. Любая помощь будет принята с благодарностью:) </p>

Ответы [ 7 ]

4 голосов
/ 14 января 2011

Почему бы вам не изменить тип i?

for (size_t i = 0; i < event.packet->dataLength - 7; i+=10) { }

Старайтесь, чтобы типы всех переменных, используемых вместе, были одного типа;следует избегать приведений.

В C ++ 03 нет спецификатора формата для size_t, вы должны привести к наибольшему типу целого числа без знака и распечатать его.(Спецификатор формата для size_t в C ++ 0x - %zu).Однако вам все равно не следует использовать printf:

std::cout << i; // print i, even if it's a size_t

Хотя потоки могут быть более многословными, они более безопасны по типу и не требуют от вас запоминания чего-либо.

Имейте в виду, что ваша реальная логика цикла может быть ошибочной.(Что происходит, как отмечает genpfault, когда dataLength - 7 отрицательно?)

2 голосов
/ 14 января 2011

Делай все с подписанной арифметикой. Попробуйте:

for (int i = 0; i < int(event.packet->dataLength) - 7; i+=10) { }

Как только вы начнете использовать арифметику без знака со значениями, которые могут быть отрицательными, и с использованием операторов сравнения, таких как <, у вас возникнут проблемы. Намного проще держать вещи подписанными.

1 голос
/ 14 января 2011

Является ли dataLength> = 7?Если результат dataLength-7 отрицательный, если вы интерпретируете его как беззнаковый, результатом будет очень большое целое число.

0 голосов
/ 29 июня 2015

Так как event.packet->dataLength возвращает тип без знака size_t:

1) Используйте size_t в качестве типа переменной индекса.

2) Удостоверьтесь, что математика не иссякнет. @ beldaz . Вместо того чтобы вычитать 7 из event.packet->dataLength, добавьте 7 к i.

// for (int i = 0; i < event.packet->dataLength - 7; i+=10) { }
for (size_t i = 0; i + 7 < event.packet->dataLength; i += 10) { }
0 голосов
/ 14 января 2011

"каждый раз, когда я делаю что-то подобное или пытаюсь сделать конверсию, часть i <# - это огромное число." </p>

Это означает, что исходная длина пакета меньше 7 (вы вычитаете 7).

Одним из исправлений является использование на практике достаточно большого целочисленного типа со знаком, и стандартная библиотека предоставляет для этой цели ptrdiff_t. Мол,

#include <stdlib.h>   // Not sure, but I think it was this one.

typedef ptrdiff_t    Size;
typedef Size         Index;

void foo()
{
    // ...
    for( Index i = 0; i < Size( event.packet->dataLength ) - 7; i += 10 )
    {
        // ...
    }
}

Более громоздкий обходной путь - встроить все это в if, который проверяет, что размер не меньше 7.

Приветствия & hth.,

0 голосов
/ 14 января 2011

Вы должны сначала проверить, если event.packet->dataLength < 7. Теперь, если оно меньше 7, вы получите значения меньше 0, используемые как беззнаковые 0 = 0x00000000; -1 = 0 - 1 = 0xFFFFFFFF.

Опять чек:

if (event.packet->dataLength < 7) {
  ...
} else {
  for (size_t i = 0; i < event.packet->dataLength - 7; i+=10) { }
}
0 голосов
/ 14 января 2011

Используйте size_t для i.

Для printf, если у вас нет C99, только C90, приведен к беззнаковому длинному или беззнаковому длинному длинномуНапример:

for (size_t i = 0; i < 10; ++i)
        //printf("%llu\n", (unsigned long long)i);
        printf("%lu\n", (unsigned long)i);

В противном случае используйте% zu

...