Какова потеря данных при преобразовании uintmax_t в size_t и unsigned int? - PullRequest
3 голосов
/ 09 октября 2011

Я получаю это:

предупреждение C4244: «инициализация»: преобразование из «uintmax_t» в «unsigned int», возможная потеря данных

on:

boost::shared_array<char> buffer( new char[file->size]);

… и затем:

предупреждение C4244: «аргумент»: преобразование из «uintmax_t» в «size_t», возможная потеря данных

on:

boost::asio::write(*socket, boost::asio::buffer(buffer.get(), file->size));

Мне будет страшно или все в порядке?

Ответы [ 3 ]

4 голосов
/ 10 октября 2011

Вероятно, file->size имеет тип uintmax_t, который больше, чем size_t, который operator new[] принимает за размер массива.Обычно первый может быть 64-битным целым, а второй - только 32-битным.

Практически это приведет к проблемам при попытке обработать файлы размером более 4 ГБ, поскольку size_t не может представлятьтакое большое количество байтов.Если вы ожидаете обрабатывать только файлы меньшего размера, где size_t достаточно велико для хранения размера файла, проблем не будет.

3 голосов
/ 10 октября 2011

Это зависит от реализации.

uintmax_t - это самый большой тип без знака, предоставляемый реализацией.size_t - это тип результата оператора sizeof, достаточно большой, чтобы вместить любой объект.unsigned int - это, конечно, беззнаковая версия типа int.

Единственные гарантии состоят в том, что size_t и unsigned int оба имеют по меньшей мере 16 бит (но, вероятно, будут больше),uintmax_t составляет не менее 64 бит (при условии правил C99), а uintmax_t по меньшей мере такой же ширины, как и любой другой тип без знака.

Предположительно file->size - это размер в байтах файла, и онвероятно, типа uintmax_t.В зависимости от системы максимальный размер файла может быть больше, чем размер любого возможного объекта в памяти.

Если размер этого конкретного файла не слишком велик, проблем нет.Но если size_t равен 32 битам (подразумевается, что объекты не могут быть больше 4 гигабайт), а ваш файл, скажем, 5 гигабайт, то вы не сможете выделить буфер в памяти, достаточно большой для хранениясодержимое файла.

А максимальное значение size_t, SIZE_MAX - это только верхняя граница максимального размера объекта.То, что SIZE_MAX равно 2 ** 31-1, не обязательно означает, что вы действительно можете создать такой большой объект.

0 голосов
/ 10 октября 2011

Это зависит от размера ваших файлов.

Большинство компьютеров имеют больший объем дискового пространства, чем ОЗУ, и во многих случаях могут поддерживать один файл, слишком большой для размещения в ОЗУ.В таком случае выделение может завершиться неудачей или размер файла может быть сокращен до размера указателя, и в этом случае вы выделите буфер, который недостаточно велик для хранения файла.

Выможет обнаруживать файлы чрезмерного размера с помощью:

size_t buffersize(file->size);
if (buffersize != file->size) { /* error, file too large to fit into virtual memory */ }
/* use buffersize for buffer allocation */

Это также приведет к удалению предупреждений.

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