[c] Следует ли приводить типы?
Вроде как int-ы автоматически приводятся туда-сюда.
Где-то видел табличку названий архитектур в зависимости от соотношения длины в них стандартных Си-типов. Не уверен 100%, но кажется, во всех Windows sizeof(long) = sizeof(int)
Если код компилируется на какой-либо платформе, он будет компилиться везде. Ибо стандарт.
В любом случае, для компилятора unsigned int != unsigned long, следовательно так как все компилится, он производит приведение типов самостоятельно.
В любом случае, для компилятора unsigned int != unsigned long, следовательно так как все компилится, он производит приведение типов самостоятельно.
При преобразование unsigned int в unsigned long по стандарту возможна потеря точности, так как в стандарте не написанна, что у них одинаковый размер. Написанно, что он меньше или равен. На всех совремменных win платформах, начиная с 95, он одинаковый .
Потеря точности у может быть у вещественных чисел. Целые числа и так точны. Тут, вероятно, стоит говорить о возможном переполнении.
Какая потеря / переполнение может быть при переходе от меньшего типа к большему?
Какая потеря / переполнение может быть при переходе от меньшего типа к большему?
Если код компилируется на какой-либо платформе, он будет компилиться везде. Ибо стандарт.
Совершенно НЕверно. Еще более ошибочно утверждение о том, что если программа работает на одной платформе, то она будет работать везде.
На всех совремменных win платформах, начиная с 95, он одинаковыйДаже на 64-битных?
int нормально расширится до long.
Ничего тут делать не надо.
Ничего тут делать не надо.
Ага, спасибо. Значит для винды оставлю 1й вариант.
А в целях общего образования: если у нас аналогичная ситуация и не винда, то какой из этих вариантов? Или вообще не так?
А в целях общего образования: если у нас аналогичная ситуация и не винда, то какой из этих вариантов? Или вообще не так?

Ну по логике вещей расширение делается автоматически, а на сужение компилятор выдаст предупреждение (если его попросить выдавать предупреждения).
Явное преобразование подавит предупреждение, но тут надо понимать, что больший тип в меньший в любом случае не влезет. Если реально используется значение, которое не умещается в меньший тип, ты его потеряешь.
Далее, ты действительно пишешь на С, а не на C++? В последнем случае следует использовать другие операторы приведения типов.
Явное преобразование подавит предупреждение, но тут надо понимать, что больший тип в меньший в любом случае не влезет. Если реально используется значение, которое не умещается в меньший тип, ты его потеряешь.
Далее, ты действительно пишешь на С, а не на C++? В последнем случае следует использовать другие операторы приведения типов.
Хм. Сначала, честно говоря, не поверил, что для того чтобы компилятор ругался на присвоение short'у long'а нужно ему что-то сказать. Проверил: оказывается нужно. Только вот фиг знает что: gcc.info проглядел, но все -W... похожие по описанию точно так же молчат.
Кто-нибудь из работавших c gcc нужную опцию не подскажет?
p.s. Да, на чистом си.
Кто-нибудь из работавших c gcc нужную опцию не подскажет?
p.s. Да, на чистом си.
А при чем тут, собсно, винда? Я бы понял, если бы это определялось архитектурой, конкретным железом или в конце концов по разному разными компилаторами. Но почему именно винда?
-pedantic ?
А у тебя оно работает? У меня тишина:
-pedantic ?
test.c:
int main(void) {
long testl = 65636;
short tests = testl;
return 0;
}gcc -pedantic test.c
хз, вроде должно. мне лень проверять, честно говоря.
мб -Wall -pedantic ?
я щас в ман заглянул, на как-то там много. ну его нах. =)
мб -Wall -pedantic ?
я щас в ман заглянул, на как-то там много. ну его нах. =)
Мне не лень, я проверил. У меня тишина. Так что вовсе и не "вроде должно"
я все свое компилирую с -Wall -pedantic, руками отрубая то, что мне не хочется видеть.
хз, вроде беглое прочтение мана показало, что это самый ворнингообильный набор опций.
хз, вроде беглое прочтение мана показало, что это самый ворнингообильный набор опций.
Не уверен 100%, но кажется, во всех Windows sizeof(long) = sizeof(int)У тебя уже неизлечимая стадия виндузятника. "Во всех виндовс" — это, конечно, перл. А ты задумывался, что это не от современности современной ОС виндовс зависит, а от платформы? Впрочем, виндузятники не думают, они себе поставят 5 виндовсов и будут "тестировать".

По поводу вопроса аффтора треда — твоя функция ExitProcess — это что? Обертка над exit? если да, то возвращается при выходе программы int, но чаще всего делают так: при ошибке возвращают -1. Если тебе надо уточнить какой именно был результат выхода — пиши в соотв. лог ПОЛНУЮ ДИАГНОСТИКУ, а не дурацкий номер ошибки. И вот почему:
Сама идея кода возврата из приложения — это вернуть "успех" или "провал". Сделано это в основном для такого типа вещей: "prog_a && prog_b && prog_c", чтобы оборвать цепочку: если какая-то из программ не отработала. После обычного запуска твой код возврата теряется, если не был вытащен специально, например, когда ты процесс запускаешь из другого и смотришь код возврата. Опять же, и в том случае лучше о провале сообщить кратко "-1", и как-то по-другому передать полную диагностику.
Почему не стоит передавать именно сам код ошибки? Всё просто — толку от него будет не много. "Can't open file" — сразу встает вопрос какой. "Пермишн денаед" — где и кому, и за что? Во всех таких случаях нужна _ПОДРОБНАЯ_ диагностика: что за ошибка, при попытке чего, что именно не так. В некоторых случаях стоит также написать типичные причины и методы их устранения.
При таком подходе твоя программа будет вызывать любовь к себе и к её аффтару.
У тебя уже неизлечимая стадия виндузятника. "Во всех виндовс" — это, конечно, перл. А ты задумывался, что это не от современности современной ОС виндовс зависит, а от платформы? Впрочем, виндузятники не думают, они себе поставят 5 виндовсов и будут "тестировать".В основном это зависит от компилятора. Платформа просто накладывает какие-то рамки.
По поводу вопроса аффтора треда — твоя функция ExitProcess — это что? Обертка над exit?
В Windows ExitProcess - функция WinAPI. Стандратная функция exit реализована через неё.
Вообще говоря, ничто не мешает выводить отадочную информацию, а потом всё-таки возвращать с помощью exit код ошибки.
Тоже попробовал, и тоже gcc не ругается.
Но вот на такой код он все же ругнулся
Но вот на такой код он все же ругнулся

dsme /tmp $ cat test.c
int main (void) {
int test = 0x100000000ul;
(void) test;
return 0;
}
dsme /tmp $ make
gcc -O0 -W -Wall -ansi -pedantic test.c -o test
test.c: В функции ‘main’
test.c:2: предупреждение: переполнение при неявном преобразовании константы
Проблема в том что автор треда не правильно написал. ExitProcess - на вход получает UINT, а GetLastError возвращает DWORD. Так что проблема теоритически существует.
Да, my bad
Хотя, по приведению к (UINT) ниже в посте понятно, что ошибся...
А ведь два раза вчера перечитал прежде чем отправить
Исправил.
Хотя, по приведению к (UINT) ниже в посте понятно, что ошибся...А ведь два раза вчера перечитал прежде чем отправить

Исправил.
Ну, небеглое прочтение показывает, что -Wall врубает далеко не все warning'и.
Вот зафигачил все что нашел для C в gcc.info в один батник (чтобы не разъезжалось разбил строку обратными слешами):
Не включил опции -Wtraditional, -Wsystem-headers и -Wlarger-than-LEN
И один фиг gcc молчит зараза такая!
Вот зафигачил все что нашел для C в gcc.info в один батник (чтобы не разъезжалось разбил строку обратными слешами):
gcc test.c -O2 -Wdisabled-optimization -pedantic -Werror -Wall -Wextra -Wfloat-equal -Wdeclaration-after-statement -Wundef -Wendif-labels \
-Wshadow -Wpointer-arith -Wbad-function-cast -Wcast-qual -Wcast-align -Wwrite-strings -Wconversion -Waggregate-return -Wstrict-prototypes \
-Wold-style-definition -Wmissing-prototypes -Wmissing-declarations -Wmissing-noreturn -Wmissing-format-attribute -Wpacked \
-Wpadded -Wredundant-decls -Wnested-externs -Wunreachable-code -Winline -Winvalid-pch -Wlong-long
Не включил опции -Wtraditional, -Wsystem-headers и -Wlarger-than-LEN
И один фиг gcc молчит зараза такая!

Вообще говоря, Windows не является кроссплатформенной ОС, и существует очень ограниченный набор систем, на которых она запускается. Происходит это, в частности, ввиду того, что во всех системных библиотеках и заголовочных файлах используются определенные соглашения, такие как sizeof(long) == sizeof(int). Таким образом, твое замечание не только необдуманное и глупое, но и свидетельствует о банальном незнании матчасти.
Оставить комментарий
feliks28
Есть ситуация:Это функции из WinApi, где ExitProcess принимает параметр UINT (unsigned int а GetLastError возвращает параметр DWORD (unsigned long)
Т.к. у меня на компьютере int равен long, то все прекрасно компилируется. А что произойдет на компьютерах, где int не равен long'у?
И как оформить код с прицелом на такой случай? Как выше? Или
Или?
Кстати, добавил в начало #define STRICT, думал ругаться начнет, но тишина. А в каких случаях тогда будет ругаться?
Компилятор gcc 3.4.5 (mingw special)