2014 dxdy logo

Научный форум dxdy

Математика, Физика, Computer Science, Machine Learning, LaTeX, Механика и Техника, Химия,
Биология и Медицина, Экономика и Финансовая Математика, Гуманитарные науки




На страницу Пред.  1, 2, 3, 4, 5 ... 7  След.
 
 
Сообщение22.11.2005, 09:06 
Что такое "char dummy[80] " ? Откуда взялось это "80" ?
Совершенно не понятно.

 
 
 
 
Сообщение22.11.2005, 14:36 
To LynxGAV:
По поводу правил хорошего тона в С/С++
Я бы посоветовал:
1. Джамса К. "1001 совет по C/C ++", но ее в электронном виде на русском я не видел.
2. Ален И. Голуб "Правила программирования на С и С++" - нашел на скорую руку в формате MSWord, есть в PDF - обычно выложено в сети под названием golub.pdf. Также есть на сайте www.realcoding.net в HTML-формате + куча другой полезной литературы для начинающих.

Ну и конечно же "Приемы объектно-ориентированного проектирования (Патерны проектирования)" - PDF есть здесь, online HTML здесь. Причем второй вариант немного дополненный.

В "1001 совет по C/C ++" - по-моему там загоняют про предпочтительность использования префиксной формы операторов ++ и --. Но, ИМХО, это просто дело привычки, это тоже самое, что писать a + b*c вместо a+b*c и ставить пробелы между if и скобкой (if () вместо if()). Я лично пишу i++ и ставлю пробелы, а кто-то нет, и это дело привычки:)).

 
 
 
 
Сообщение22.11.2005, 14:43 
char dummy[80] - это классика, вспомогательный буфер для null-terminated string.
еще обычно пишут что-нить типа
#define MAX_STR_LEN 80
......
char dummy[MAX_STR_LEN];
и вместо sizeof(dummy) - MAX_STR_LEN.

а 80 - из серии "А зачем больше?"

 
 
 
 
Сообщение22.11.2005, 19:32 
Аватара пользователя
:evil:
Anonymous писал(а):
Что такое "char dummy[80] " ? Откуда взялось это "80" ?
Совершенно не понятно.


char dummy[80] - это временный буфер (dummy - пустышка, затычка), позволяющий считать хвост строки из потока. Его длина произвольна, и 80 ничуть не лучше и не хуже любой другой - среднепотолочное значение; лучше, чем читать по байту, и не требующее терабайтной памяти в стеке. Именно в силу среднепотолочности и локальности влияния 80 не было сделано макрой в начале программы.

По стандарту, fgets() читает до тех пор пока не выполнится одно из трех условий - наполниться буфер, или найден символ конца строки, или найден конец файла. К сожалению, если ничего не предпринимать, то слишком длинная строка в первом случае будет резаться, и читаться как несколько строк. Чтобы это предотвратить, если символ конца строки не найден в прочитанном буфере, то мы читаем и выбрасываем данные либо до конца строки, либо до конца файла.

Садизм? :D Да :!: Но эта программа, как я понимаю, больше все таки учебная, чем промышленная. Считка и отбрасывание конца предотвращает явные ошибки и нестабильность, а вот необходимости делать более сложное решение со склеиванием буферов и возвратом результата в динамическом буфере нет.

 
 
 
 
Сообщение22.11.2005, 19:51 
Аватара пользователя
:evil:
VLarin писал(а):
#define MAX_STR_LEN 80
......
char dummy[MAX_STR_LEN];
и вместо sizeof(dummy) - MAX_STR_LEN.


Лично я избегаю этой формы. Если по каким-то причинам мы, например, добавили #define MAX_SHORTSTR_LEN 40, и поменяли char dummy[MAX_STR_LEN] на char dummy[MAX_SHORTSTR_LEN], нам будет больно об этом вспоминать. Обычно это не так очевидно, например, константа входит в описание типа, и т.д. Вариант с sizeof() - безопаснее, а потому предпочтительней.

По подобной-же причине я не пишу sizeof(STAR), а пишу sizeof(*star_list) или sizeof(star_list[0]), что более точно, но обычно лень писать. Тип *star_list может со временем поменяться на SUPERSTAR, и нам предстоит веселое занятие отыскивать все вхождения комбинации STAR/star_list/sizeof().

И третий пример на ту же тему. memcpy(tgt, src, sizeof(*tgt)); гарантирует сразу несколько вещей - корректное указание количества копируемых байт и непереполнение *tgt, если типы *tgt и *src разойдутся в будущем.

 
 
 
 
Сообщение22.11.2005, 20:24 
Аватара пользователя
:evil:
VLarin писал(а):
В "1001 совет по C/C ++" - по-моему там загоняют про предпочтительность использования префиксной формы операторов ++ и --. Но, ИМХО, это просто дело привычки, это тоже самое, что писать a + b*c вместо a+b*c и ставить пробелы между if и скобкой (if () вместо if()). Я лично пишу i++ и ставлю пробелы, а кто-то нет, и это дело привычки:)).


Увы, не все привычки одинаковы. Я готов согласиться с Вами по поводу пробелов - хотя я пишу и вовсе a + b * c, и считаю, что лучше писать for (p, q; r < s; s), а не for(p ,q ;r < s ;s ), но это имеет относительно малое значение, равно как и привильное и систематическое выравнивание программы и использование табуляций в тексте (тяжкое наследие первых дней UNIX'а). В конце концов, это влияет только на читаемость программы человеком. Не могу сказать, что читаемость не важна, но - у всех свои привычки. И это вопрос уважения к читателю. Я обычно исхожу из того, что программа - это, в первую очередь, текст, и, соответственно, знаки препинания ().,;?: должны расставляться соответсвенно. Но это - мое предпочтение, и не более того.

С ++i vs i++ вопрос более тонкий. В C они более или менее эквивалентны, если возвращаемое значение не используется. В C++ эти операции могут быть переопределены, и стать неэквивалентными, что приводит к тонким и труднонаходимым ошибкам. Даже переводя на человеческий язык: "увеличить i на единицу и вернуть получившееся значение" звучит как-то лучше (более похоже на "увеличить i на единицу"), чем "запомнить текущее значение i, увеличить i на единицу, и вернуть запомненое значение". И еще. Все ничего, когда i. Ну а когда это сложное выражение? (Например, *foo(aaa)->bbb->ccc->ddd. Все законно, можно писать и ++*foo(aaa)->bbb->ccc->ddd, и *foo(aaa)->bbb->ccc->ddd++.) Нам надо дочитать его до конца, чтобы понять, что происходит. В префиксной же форме это ясно сразу. А я не немец такое читать - это они отрицание ставят в конце предложения. Так что эту привычку я все-таки рискну осудить как вредную. И последняя капля - я встречал компиляторы, которые генерируют лишний код в случае i++. А компиляторы, как и родителей, не выбирают :lol: - какой приходит с процессором, такой и есть. А вот от привычек иногда трудно избавляться ("Бросить курить очень просто. Я сам это делал тысячу раз").

 
 
 
 
Сообщение23.11.2005, 11:04 
Вчера прогнала у себя, выдало 15 (или около того) warnings, но удачно со всем этим делом разделалась (как писать комментарии в С я знаю :), это были не они). Кроме того наткнулась на погрешности: при редактировании данных звезды по условию располагать надо по три в строке, при сортировке по массе надо поменять порядок, если добавляла еще одну звезду и потом хотела ее отредактировать, то выдавало "щас", так что и это я поправила. С циклами, похоже, проблем :) нет.

Это все пустяки. Охотно соглашаюсь. Но ребенок разбирался.. :P

МОСКВА НЕ СРАЗУ СТРОИЛАСЬ :D

PS Еще какую-то пургу показывало "неправильно идут часы" (ох, и память! уже точно не помню как). Оно-то и верно, что неправильно идут, потому что я их просто не перевела как все, - ввиду удобства, спать ложишься на час позже, встаешь на час раньше, на работo-учебу не опаздываешь. Но наручные. Ладно, хоть роли никакой этой не сыграло, но этого юмора я не поняла.

 
 
 
 
Сообщение23.11.2005, 17:07 
To незванный гость:
Все правильно говорите.
При использовании ++i и i++ возможны ситуации, когда префикс лучше. Но я имел ввиду их обычное использование, в циклах с простыми переменными и все прочее - я обычно использую постфикс и пишу for (int i = 0; i < n; i++), тоже самое с std::iterator :).
Насколько я знаю, но могу и ошибаться, в компиляторе MS Studio и префик, и постфикс

По поводу #define MAX_STR_LEN 80 - вредная штука, я вообще стараюсь define для объявления глобальных констант не использовать, а писать например const int nMaxLength = 80. Кстати, в 1001 совет по С/С++ по этому поводу написано, что есть много причин не использовать define для констант.

А буфер char dummy[] длиной в 80 байт - это классика, это было в какой-то грамотной книге по С, многие ее читали и так это и пошло, насколько я знаю. Хотя можно было использовать что-угодно, например, степень 2 (64, 128 и т.д.), но походу в оригинале больший буфер не требовался:). Я даже где-то в исходниках MFC такое тоже встречал:).

Ну и конечно же лучше использовать sizeof вместо прямого указания размера строки.
Есть правда такое дело как Unicode, программисты из microsoft используют в исходниках MFC везде используют макро #define _countof(array) (sizeof(array)/sizeof(array[0])) для определения длины строки.

 
 
 
 
Сообщение23.11.2005, 19:25 
Аватара пользователя
:evil:
LynxGAV писал(а):
(как писать комментарии в С я знаю :), это были не они)

У мнея не было и тени сомнения, что Вы знаете. Я писал о разнице компиляторов. Строго говоря, я использовал незаконный в C синтаксис, который многие, но не все, компиляторы допускают. И у GCC с этим, по крайней мере когда-то, были проблемы.

LynxGAV писал(а):
редактировании данных звезды по условию располагать надо по три в строке, при сортировке по массе надо поменять порядок

Перед решением задачи полезно прочитать ее условие, а я не читал :D. Хотя, имейте в ввиду - у Вас максимальная длина имени звезды - 30 символов, да еще на номер и разделители место. Кто, интересно, условие придумал - все строчки разъедутся, и читать станет невозможно. Я намеренно менял с трех на два, чтобы обеспечить читаемый экран. Попробуйте 6-7 звезд подряд с именами подлинее. А вот сохранение порядка сортировки при добавлении/редактировании я пропустил мимо ушей. Всегда просто в конец добавлял. Сортировка шла только по запросу, это была операция, а не режим.

LynxGAV писал(а):
если добавляла еще одну звезду и потом хотела ее отредактировать, то выдавало "щас", так что и это я поправила

А что это было? У меня, вроде, ничего не показывало. :(

LynxGAV писал(а):
PS Еще какую-то пургу показывало "неправильно идут часы"

Это программа показывала или компилятор/линкер? Если второе, такое бывает, когда timestamp файлов находится в будущем (позже текущего времени компьютера.) Или, если ОС сверяет часы с внешним источником, и находит слишком большую разницу.

 
 
 
 
Сообщение23.11.2005, 20:11 
Аватара пользователя
:evil:
VLarin писал(а):
Но я имел ввиду их обычное использование, в циклах с простыми переменными и все прочее

Лично я, обычно, пишу единаково - "чтобы не сбивать руку". Этот очень старый шаблон (pattern) - единообразность решений - освобождает мозги для другого ("У того, у кого она есть" - а у меня с этим проблемы :) ).

VLarin писал(а):
писать например const int nMaxLength = 80... Кстати, в 1001 совет по С/С++ по этому поводу написано, что есть много причин не использовать define для констант.

Старую собаку новым штукам не научишь. :P Я часто пишу по старинке, хотя знаю, что неправ. В свою оправдание замечу, что const в C - явление относительно новое, и не все компиляторы его хорошо поддерживают (я встречал в описаниях фразы типа "ключевое слово const опознается, но игнорируется"). С этим методом проблемы в интерфейсах - в заголовке так просто не напишешь (если я правильно помню). Хотя были и такие, кто сомневался, а нужно ли интерфейсу знать значение - дескать, достаточно символьного имени. const нельзя применять в условной компиляции. И, наконец, всяческие экзотические игры вроде token pasting... А советы - они и есть советы, а не цитатник Мао. Я обычно советы слушаю, а решаю сам.

VLarin писал(а):
А буфер char dummy[] длиной в 80 байт - это классика, это было в какой-то грамотной книге по С

Я dummy (да еще scratch) видел еще в примерах к OS/360 - была такая система в 60-е годы. Из нее потом ЕС ЭВМ сделали. На западе ее реинкарнации до сих пор живы, и находятся люди, которые часто и помногу пишут на ее ассемблере. Я услышал - не поверил.

VLarin писал(а):
Есть правда такое дело как Unicode

"Не сыпь мне соль на рану//Она и так болит". Unicode в C++ - это большая "проблема". Особенно в обработке строк - в mem*() или alloc() нужна длина, в строковых функциях - количество символов. Макротрюк очень старый, я такое макро всегда называл dim(). Было у меня еще одно, offs(), вычислявшее смещение поля в структуре: #define offs(T, field) ((int)&((T*)(NULL)->f)). И опять, у некоторых компиляторов с ним проблемы. До C++ указателей на элементы структуры очень помогало жить, да и сейчас помогает.

 
 
 
 
Сообщение23.11.2005, 20:28 
Цитата:
А что это было? У меня, вроде, ничего не показывало. :(


Незванный гость..Хмм..А если к исходным добавить еще одну звезду. А потом скажем, последних две отредактировать.
Честно, не было и минуты, я так быстро все это дело просматривала, но верю, что не ошиблась.
А с часами - да, в компилляторе. Теперь узнаю:
Цитата:
когда timestamp файлов находться в будущем (позже текущего времени компьютера.


По-любому проект (хе-хе..смеюсь) уже сдан :D Теперь приходится смотреть в окно и думать, дальше будет что-то посложнее или попроще, или дальше ничего не будет.

VLarin, спасибо за литературу (меня англ. не пугает, можете еще посоветовать :) ). Как только что-то прояснится, так сразу и начну ознакамливаться с т.н. правилами хорошего тона (подозреваю размещенными на сотнях страниц).

А вообще, ребята, для меня вы начали говорить по-китайски. Но главное себя комфортно чувствовать, - можно и тапочки пушистые :wink: одеть.

"От провокаторов жены уходят". Люблю, однако, провокации :D

 
 
 
 
Сообщение23.11.2005, 21:13 
Аватара пользователя
:evil:
LynxGAV писал(а):
А если к исходным добавить еще одну звезду.

:oops: Виноват-с. В correct_star() условие
    if ((num < 1) || (num >= star_list->Num_stars)) {
должно быть
    if ((num < 1) || (num > star_list->Num_stars)) {
Я сделал нумерацию с единицы, а условие прозевал...

LynxGAV писал(а):
говорить по-китайски

О, священные войны о языке и стиле! Ну, пока до кровопролития не дошло, дипломатия, однако-с.

LynxGAV писал(а):
"От провокаторов жены уходят". Люблю, однако, провокации :D

"Вот так всегда бывает с теми, кто неожиданно бросает пить."

 
 
 
 
Сообщение23.11.2005, 21:26 
Советы на то и советы, чтобы к ним прислушиваться, а делать по своему:)
В книгах, которые я упоминал ранее, воды написаны много. Но есть и куча полезных советов. Так что, советую посмотреть на досуге, может найдете что-нить интересное для себя. А "патерны проектирования" - это просто шедевр.

 
 
 
 
Сообщение23.11.2005, 21:31 
LynxGAV писал(а):
А если к исходным добавить еще одну звезду.


Тогда не всё еще потеряно. (По отношению ко мне.)
Это не может не радовать.

Цитата:
"Вот так всегда бывает с теми, кто неожиданно бросает пить."


"А я не пью, я порядочная".

Вобщем бум ждать чего-нибудь новенького, и на этом пока покидаю обсуждение глубин и истории. Мне оно, увы, недоступно.

 
 
 
 
Сообщение25.11.2005, 21:01 
незванный гость писал(а):
:evil:
И главное - не стесняйтесь задавать вопросы! :D Очень надеюсь, их будет много. И они не иссякнут после сдачи...

Даже идиотские..
Незванный гость. Пока ехала и застряла в пробке всплыли эти плюсики. Никогда не задумывалась, а жаль.
Когда экзекьют
y=x++; (у=х; х++)
1. значение х присваивается у;
2. значение х увеличивается.
у=++х; (х++; у=х)
1. увеличивается;
2. присваивается.
х=5; у=х++;
Значения: х-6, у-5;
х=5; у=++х;
Значения: х-6, у-6;
Поэтому если ими не пользуемся, то в С все однаково. ?
Это как по модулю три переписать.

 
 
 [ Сообщений: 105 ]  На страницу Пред.  1, 2, 3, 4, 5 ... 7  След.


Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group