Б. Страуструп - Язык программирования С++. Специальное издание, 3-изд. Бином. 2004 (1160791), страница 164
Текст из файла (страница 164)
Тип иа1аггау и его вспомогательные средства разработаны для ускорения вычислений. Это отражается в некоторых ограничениях для пользоватсля и в жестких требованиях для разработчиков. В сущности, разработчику иа1аггау приходится использовать все мыслимые приемы оптимизации. Например, оггерации можно делать встроенными; считается, что операции с иа!аггау не влияют ни на какие объекты (кроме, конечно, своих явных аргументов). Также считается, что массивы иа1агтау не имеют альтернативных имен, и при сохранении базовой семантики допускается введение вспомогательных типов и устранение временных массивов.
Таким образом, обьявления в <иа1аггау> могут выглядеть пе так, как здесь (и в стандарте), но они должны обеспечивать те же самые операции с тем же самым смыслом для всех программ, написанных в рамках правил. В частности, элементы иа1агтау должны иметь обычную семантику копирования (з 17.1 4). Глава 22. Численные методы 732 ,с,л слс. Э 22.4.б //с . б 22.4.В //слс. 9 22.4.9 // см. ф 22.4.9 оа(алтсау орега1ог[] [яйсе) сопя(, яйсе аггау<Т орега(ог[] )к(!сег оа(аггау орега1огЦ [сопя1 ук((сей) сопя1; уя(ссе аггау<Т орега1ог[) [сопк1укйсей) оа1аггау орега(ог[] )сопя1па!аггау<боо(ьй) сопя(; таку аггау<Т орега1ог[] )сопя! оа!аггау<(соо(эй), оа1аггау орега1ог[] [сопя1оа1аггау<ксяе !я0) сопя(; !адрес! астау<Т орега!ос[] [сопя(оа(аггау<иле 1>й)с //слс.
9 22.4.б //см. 9 22.4.8 //см. ф 22.4.9 /,с см. 9 22 ай ! О оа!астауй орега!ог= [сопя! кйсе аггау<Т й) оа(аггауй орега1ог= [сопя1 укусе аггау<Тьй) оа(аггауй орега1ог-. [сопл1таяя аггау<Т й) оа(аггауй орега!ог= [сопк1 !пд!гес! аггау<Тлй)' 22.4.3. Операции-члены Вводятся очевидные, а также и не совсем очевидные функции-члены: 1етр(а!е<с(акя Т с(акк оа1аггау ( рабус: оа(аггауй орега(ог'= [сопя! Тй агу); // о[с]'=агу для каждого элелсента //анвлогпкпос/=, влл=, +=, -=, "=, й=,)=, «=и»= // сулсма элемептов, использует += для сложения Т кит [) сопя!; Массив оо1оггоу можно присвоить другому того же размера. Как и предполагалось, о1=о2 копирует каждый элемент о2 в соответствующую позицию объекта о1.
Если вектора имеют разный размер, результат присваивания не определен. Поскольку оа1ап ау придуман для оптимизации скорости, было бы наивно предполагать, что присваи ванне об ьекта оа1аггад неправильного размера приведет к легко выявляемой ошибке (такой как исключение) или какому-либо другому <осмысленному> поведению. Кроме такого общепринятого присваивания, массиву оа(аг ау можно присвоить скаляр. Например, о= 7 присваивает каждому элементу о значение 7. Это может показаться странным; лучше всего понимать это как иногда применяемый вырожденный случай оператора присваивания Я 22А.З).
Индексация целым числом ведет себя обычным образом и не выполняет проверки диапазона. Кроме того для выделения отдельных элементов, индексация оа1ап ау предоставляет четыре способа извлечения подмассивов (5 22А.6). И наоборот, присваивания (и конструкторы 5 22АА) принимают такие подмассивы в качестве операндов. Набор операций присваивания для массивов оа(аггау избавляет от необхолимости преобразовгявать вспомогателы|ые массивы, такие как яйсе а!гау, в оа1аггау перед их присваиванием. Для обеспечения эффективности подобным же образом в реализации могут вводиться другие векторные операции, такие как + и *. Кроме того, для векторных операций существует много действенных врнемов оптимизации, в том числе над срезами типа яйсе и другими вспомогательными векторными типами.
733 22.4. Векторная арифметика //наименьшая величина, использует <для сравнения // наибольшая величина, использует «для сравнения 7 тгп () сопя!; Т тая () сопя!; иа1аггау зйус (!п! !) соней иа1а ггау сей! (т ! !) сопя!; иа1аггау ирр!у (Т/(7)) сопя!, //ггяи!![!)=/1и[!]) для каждого элемента иа!аггау арр1у (Т/'(сопя! Та)) сопя!; иа1аггау орега!ог-() сопя!; //гели!![!)= — и[!) для каждого элеменпш //аналогично:+, -,! Йее !иге [)сопя!, // число элел!гатов ио)й гезкге (Ыее ! и, сопя! Т8 иа1 = Т()); //и элеменпюв созна<внаем иа1 й Если я(хе ~ — О, величины яит (), тт () и тая () неопределены. Например, если и — это массив иа1аггау, то его можно масщтабнровать следующим образом: и*-.2 или и/=12й То есть применение к вектору скаляра означает применение этого скаляра к каждому элементу вектора.
Обычно, легче оптимизировать *=, чем комбинацию * и = Я 11.3.1). Отметим, что непрнсваивающие операции конструируют новый иа1аггау. Например: г1оиЫе тсг (г!онЫе г1) ( ге!игп 8+1; ) //инкременгп ио!с11'(иа1аггау<с!ои51е>8, и) ( иа1аггау<<1оиЫе> и2 = о.арр1у (тсг); // производит // инкрементированный иа! аггау' Значение и не изменяется. К сожалению, арр1у () не принимает в качестве аргуляента Я 22.9[1)) объекты-функции Ц 18А). Функции логического н циклического сдвига яЫ)! () н сяй(7! () возвращают новый иа1аггау с соответствующим образом сдвинутыми элементами, а исходный объект остается без изменений. Например, циклический сдвиг и2=и.сяй!/! (и) выдаст и(2) такой, что и2[г]==и[ (!+п)учи.я!яе Ш.
Логический сдвиг иЗ=и.я1!!?! (и) выдаст и[З), такой, что иЗ(1) равен и[!+и), если !+ и — допустимый индекс для и, а иначе иЗ[1) примет значение по умолчанию. Считается, что н яй(/! (), и сяп(/! () сдвигают влево, если им задан положительный аргумент, и вправо — если отрицательный. Например: ио!с1/[) ( !и! а1рЬа[) = [ 1, 2, 3, 4, 5, 6, 7, 8 ), иа!аггау<си! и(а1рЬа,8); иа!аггау<гп! и2= ияйф(2); иа1аггау<!п!> и3 = и«2, иа!аггау<!от> и4 = ияЫ/! ( — 2), иа!аггау>йп! и5= и»2; иа !а гтау<т г> иб = исзЬ11! [2), иа!аггау<!пт> и7 = ися?г!Т! (-2); //логический сдвиг /влево для 1<О и вправо для !>0) //чики<вский сдвиг !влево для 1<О и вправо для г>0) //1,2,3,4,5,6,?,8 //3, 4, 5, 6, 7, 8, О.
0 //4, 8, ! 2, 16. 20, 24, 28, 32 //0,0, 1,2,3,4,5,6 0 О, О, О, 1, 1, 1, 1, 2 // 3, 4, 5, 6, 7, 8, 1, 2 // 7, 8, 1, 2, 3, 4, 5, 6 Глава 22. Численные методы оо!дава!аггау<!>>г> ой оа1алтау<доиЫе> од) ( Ы «= 2; л>л Ы[!)«=2 для всех алел>ентов Ы од «= 2; ллл> ошибка: для значений с плавающей точкой сдвиг неопределен ) Размер массива оа1аггау можно изменить, однако гез!яе () -- не та операция, которая предназначена для превращения оа1аг ау в структуру данных, способную динамически расти, как вектора или строки. 1[ля оа1аг ау гез!ее () — это операция повторной инициализации, которая заменяет существующее содержимое оа1аггау набором значений по умолчанию. Старые значения утрачиваются.
Часто оа1аг ау после вызова функпии гез!ге () становится тем, что мы создаем в качестве пустого вектора. Рассмотрим, как можно инициализировать оа1аггау нз ввода: оо!д Г() ( !п! п=О, сгп»п, ллг читаем разллер массива с! (и<=0) еггог (" неверные границы массива" ); оа!а~тауке!ои6!е> о (п); >Лл> создаем массив подходящего размера шг 1=0, шЬ!е (><и д<ч, с!п ' о[!<-ч-)) >>> заполняем>>ассов >Г (![=и) еггог (' введено слишком мало элементов'); 0- ) Если мы захотим обработать ввод в отдельной функции, это можно сделать так: ооЫ та!а!!ге ~сот шри! (оа!аггау<йои6!е>й о) ( шг и=у; с!г»> и; л>л> чатае,ч разл>ер л>ассизи !1' (и<=0) еггог ("неверные границы массива' ), ил ез!ге [и); >>л> создаел> массив подходящего разл>ера !п! >=О; ш6!!е (!<и а<> с!п»о[!л-ч-))> !! заполняел> л>ассов гл' (!(=п) еггог('введено слишком мало элементов ); ооЫО () ( оа!аггау<доссЫе> о; !и!!!а!!гергот !при!(о); л>лл создаел> массив по ул>олчанию О ин>щиализиция о с правильныл> раз>>ерол> >>/ а допуспи>л>ь>лш элементалш Для массивов оа1аггау операторы «и» — это операторы битового сдвига, а не опе- раторы сдвига элементов или вводал'вывода (2 22А.4).
Следовательно, чтобы сдви- гать биты внутри алементов интегрального типа, можно пользоваться операторами «= и»ьч Например: 735 22.4. Векторная арифметика Это позволяет избежать копирования больших объемов данных. Если нам нужно, чтобы массив иа1аггау с ценными данными динамически рос, мы должны воспользоваться временным массивом для хранения: ио!с1 Ого и (иа1ап ау<т1>й и, Ыее 1 и) ( Ял =и.ятге ()) ге1игп; иа1аггау<!пс> 1тр (и); // временно й ииссив; и элел~ентов по улюлч азию сору (йи(О], йи(ия!ее ()], й1тр(О]); //нопируюи(ий олгорипьи из з" 13.6.! и.гея!ее (и), сору (йгтр(О], йгтр(и.з!ге ()], йи(О]); Т/в предполагается, что массивы иа1аггау будут использоваться таким образом.