Главная - Литература

0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 [81] 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294

читает значение цвета. Так часто делают при разработке интерактивных приложений, предоставляющих возможность настройки их параметров.

Кроме того, время связывания может определяться тем, когда вызывается метод ReadTitleBarColorQ. Его можно вызывать при загрузке программы, при создании окна или при каждой перерисовке окна: каждый последующий вариант соответствует все более позднему времени связывания.

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

при написании кода (с использованием магических чисел);

при компиляции (с использованием именованной константы);

при загрузке программы (путем чтения значения из внешнего источника, такого как реестр Windows или файл свойств Java);

при создании объекта (например, путем чтения значения при каждом создании окна);

по требованию (например, посредством чтения значения при каждой перерисовке окна).

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

10.7. Связь между типами данных и управляющими структурами

Между типами данных и управляющими структурами существуют четко определенные отношения, впервые описанные британским ученым Майклом Джексоном (Jackson, 1975). В этом разделе мы их вкратце обсудим.

Джексон проводит связи между тремя типами данных и соответствующими управляющими структурами.

Последовательные данные соответствуют последо-

вательности команд Последовательные данные (sequen- доватеньно» тщрт ьытть-tial data) - это набор блоков данных, используемых в оп- иий ттр, теву 14 ределенном порядке (рис. 10-2). Если у вас есть пять команд

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



ных ояараторах см. главу 15.

Рис. 10-2. Последовательными называются данные, обрабатываемые в определенном порядке

Селективные данные соответствуют операторам if и case Вообще селективные данные (selective data) представляют собой набор, допускающий использование одного и только одного элемента данных в каждый конкретный момент времени (рис. 10-3). Соответствующими командами, выполняющими фактический выбор данных, являются операторы if-tben-else или case. Так, программа расчета зарплаты должна была бы выполнять разные действия в зависимости от того, какой является оплата труда конкретного сотрудника: сдельной или повременной. Опять-таки шаблоны кода соответствуют шаблонам данных.


Рис, 10-3. Селективные данные допускают использование только одного из нескольких элементов

Шцятшш ссылка О циклах сй. таву 16.

Итеративные данные соответствуют циклим Итеративные данные (iterative data) представляют собой данные одного типа, повторяющиеся более одного раза (рис. 10-4). Обычно они хранятся как элементы контейнера, записи файла или элементы массива. Скажем, вы могли бы хранить в файле список номеров карточек социального обеспечения, для чтения которого было бы разумно использовать соответствующий цикл.


Рис, 10-4, Итеративные данные повторяются

Реальные данные могут быть комбинацией последовательных, селективных и итеративных данных. Для описания сложных видов данных подойдет комбинация простых.



10.8. Единственность цели каждой переменной

Есть несколько тонких способов использования переменных более чем с одной целью, однако подобных тонкостей лучше избегать.

Используйте каждую переменную только с одной целью Иногда есть соблазн вызвать одну переменную в двух разных местах для решения двух разных задач. Обычно в таких случаях переменной приходится присваивать неудачное имя, соответствующее одной из ее целей, или использовать для решения обеих задач «временную» переменную (как правило, с бесполезным именем х или temp). Следующий пример иллюстрирует использование временной переменной с двойной целью:

ШПример использования переменной с двойной целью -плохой подход (С++)

Вычисление корней квадратного уравнения.

Предполагается, что дискриминант (b*b-4*a*c) неотрицателен.

temp = Sqrt( b*b - 4*а*с );

root[0] = ( -b + temp ) / ( 2 * a );

root[1] = ( -b - temp ) / ( 2 * a );

корни меняются местами temp = root[0]; root[0] = root[1]; root[1] = temp;

Вопрос: какие отношения связывают temp в первых строках кода и temp в последних? Ответ: никакие. Из-за использования в обоих случаях одной переменной создается впечатление, что две задачи связаны, хотя на самом деле это не так. Создание уникальных переменных для каждой цели делает код понятнее. Вот улучшенный вариант:

Пример использования двух переменных для двух целей -хороший подход (С++)

Вычисление корней квадратного уравнения.

Предполагается, что дискриминант (b*b-4*a*c) неотрицателен.

discriminant = Sqrt( b*b - 4*а*с );

root[0] = ( -b + discriminant ) / ( 2 * a );

root[1] = ( -b - discriminant ) / ( 2 * a );

Пщщттш штя Парамет-рь1 методов также дояжну иметь только одну цш. О параметрах штодов т. раздел 7.5.

корни меняются местами oldRoot = root[0]; root[0] = root[1]; root[1] = OldRoot;



0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 [81] 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294



0.0025