Jump to content

Задание (информатика)

(Перенаправлено из оператора присваивания )

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

Сегодня наиболее часто используемое обозначение для этой операции: x = expr (первоначально Superplan 1949–51, популяризированный Fortran 1957 и C ). Вторым наиболее часто используемым обозначением является [1] x := expr (первоначально АЛГОЛ 1958 года, популяризированный Паскалем ). [2] Также используются многие другие обозначения. В некоторых языках используемый символ рассматривается как оператор (это означает, что оператор присваивания в целом возвращает значение). Другие языки определяют присваивание как оператор (это означает, что его нельзя использовать в выражении).

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

Семантика

[ редактировать ]

Операция присваивания — это процесс в императивном программировании , в котором с течением времени с определенным именем переменной связываются разные значения. [1] Программа в такой модели работает, изменяя свое состояние с помощью последовательных операторов присваивания. [2] [3] Примитивы императивных языков программирования полагаются на присваивание для выполнения итерации . [4] На самом низком уровне присвоение реализуется с помощью машинных операций, таких как MOVE или STORE. [2] [4]

Переменные — это контейнеры для значений. В переменную можно поместить значение, а затем заменить его новым. Операция присваивания изменяет текущее состояние исполняемой программы. [3] Следовательно, присвоение зависит от концепции переменных . В задании:

  • The expression оценивается в текущем состоянии программы.
  • The variable присваивается вычисленное значение, заменяющее предыдущее значение этой переменной.

Пример: Предполагая, что a — числовая переменная, присвоение a := 2*a означает, что содержимое переменной a удваивается после выполнения оператора.

Пример сегмента кода C :

int x = 10; 
float y;
x = 23;
y = 32.4f;

В этом примере переменная x сначала объявляется как целое число, а затем ему присваивается значение 10. Обратите внимание, что объявление и присвоение происходят в одном операторе. Во второй строке y объявляется без присвоения. В третьей строке x ему присваивается значение 23. Наконец, y присвоено значение 32,4.

Для операции присваивания необходимо, чтобы значение expression четко определен (это допустимое значение rvalue ) и что variable представляет изменяемый объект (это допустимое изменяемое (неконстантное ) значение lvalue ). В некоторых языках, обычно динамических , нет необходимости объявлять переменную перед присвоением ей значения. В таких языках переменная автоматически объявляется при первом присвоении, причем область ее объявления варьируется в зависимости от языка.

Одно задание

[ редактировать ]

Любое присвоение, которое изменяет существующее значение (например, x := x + 1) запрещено в чисто функциональных языках. [4] В функциональном программировании присваивание не рекомендуется в пользу одиночного присваивания, более известного как инициализация . Одиночное присвоение является примером привязки имени и отличается от присвоения, описанного в этой статье, тем, что его можно выполнить только один раз, обычно при создании переменной; последующее переназначение не допускается.

Вычисление выражения не имеет побочного эффекта , если оно не меняет наблюдаемое состояние машины. [5] кроме получения результата, и всегда выдает одно и то же значение для одного и того же ввода. [4] Императивное присваивание может привести к побочным эффектам, разрушая и делая старое значение недоступным при замене его новым. [6] это называется деструктивным присвоением По этой причине в LISP и функциональном программировании , аналогично деструктивному обновлению .

Одиночное присваивание — единственная форма присваивания, доступная в чисто функциональных языках, таких как Haskell , которые не имеют переменных в смысле императивных языков программирования. [4] а скорее именованные постоянные значения, возможно, составной природы, с их элементами, постепенно определяемыми по требованию , для ленивых языков. Чисто функциональные языки могут предоставить возможность выполнять вычисления параллельно , избегая узкого места фон Неймана , связанного с последовательным выполнением по одному шагу, поскольку значения не зависят друг от друга. [7]

Нечистые функциональные языки обеспечивают как одиночное, так и истинное присваивание (хотя истинное присваивание обычно используется реже, чем в императивных языках программирования). Например, в Scheme оба одиночных присваивания (с let) и истинное присваивание (с set!) можно использовать для всех переменных, а для деструктивного обновления внутри списков, векторов, строк и т. д. предусмотрены специализированные примитивы. В OCaml переменным разрешено только однократное присвоение через метод let name = value синтаксис; однако деструктивное обновление может использоваться для элементов массивов и строк с отдельными <- оператор, а также поля записей и объектов, которые были явно объявлены изменяемыми (то есть способными быть изменены после их первоначального объявления) программистом.

Языки функционального программирования, использующие одно присваивание, включают Clojure (для структур данных, а не переменных), Erlang (он допускает множественное присваивание, если значения равны, в отличие от Haskell), F# , Haskell , JavaScript (для констант), Lava, OCaml , Oz (для переменных потока данных, а не ячеек), Racket (для некоторых структур данных, таких как списки, а не символы), SASL , Scala (для значений), SISAL , Standard ML . без возврата Код Пролога можно считать явным однократным присвоением, явным в том смысле, что его (именованные) переменные могут находиться в явно неназначенном состоянии или быть установлены ровно один раз. В Haskell, напротив, не может быть неназначенных переменных, и каждую переменную можно рассматривать как неявно установленную при ее создании в свое значение (или, скорее, в вычислительный объект, который будет выдавать свое значение по требованию ).

Ценность задания

[ редактировать ]

В некоторых языках программирования оператор присваивания возвращает значение, а в других — нет.

В большинстве языков программирования, ориентированных на выражения (например, C ), оператор присваивания возвращает присвоенное значение, что позволяет использовать такие идиомы, как x = y = a, в котором оператор присваивания y = a возвращает значение a, который затем присваивается x. В таком заявлении, как while ((ch = getchar()) != EOF) {}, возвращаемое значение функции используется для управления циклом при присвоении того же значения переменной.

В других языках программирования, например в Scheme , возвращаемое значение присваивания не определено, и такие идиомы недопустимы.

В Хаскеле [8] нет присваивания переменных; но операции, подобные присваиванию (например, присвоение полю массива или полю изменяемой структуры данных), обычно оцениваются по типу единицы , который представлен как (). Этот тип имеет только одно возможное значение и поэтому не содержит никакой информации. Обычно это тип выражения, который оценивается исключительно из-за его побочных эффектов.

Варианты форм поручения

[ редактировать ]

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

Дополненное задание

[ редактировать ]

Случай, когда присвоенное значение зависит от предыдущего, настолько распространен, что многие императивные языки, особенно C и большинство его потомков, предоставляют специальные операторы, называемые расширенным присваиванием , например *=, так a = 2*a вместо этого можно записать как a *= 2. [3] Помимо синтаксического сахара, это помогает компилятору, ясно давая понять, что модификация переменной на месте a возможно.

Связанное назначение

[ редактировать ]

Заявление вроде w = x = y = z называется цепным присваиванием , в котором значение z присваивается нескольким переменным w, x, и y. Связанные присваивания часто используются для инициализации нескольких переменных, как в

a = b = c = d = f = 0

Не все языки программирования поддерживают цепное присваивание. Связанные задания эквивалентны последовательности заданий, но стратегия оценки различается в зависимости от языка. Для простых связанных присвоений, таких как инициализация нескольких переменных, стратегия оценки не имеет значения, но если целевые значения (l-значения) в задании каким-либо образом связаны, стратегия оценки влияет на результат.

В некоторых языках программирования ( например , C ) поддерживаются цепочки присваиваний, поскольку присваивания являются выражениями и имеют значения. В этом случае цепное присвоение может быть реализовано с помощью право-ассоциативного присваивания , а присвоения выполняются справа налево. Например, i = arr[i] = f() эквивалентно arr[i] = f(); i = arr[i]. В C++ они также доступны для значений типов классов путем объявления соответствующего возвращаемого типа для оператора присваивания.

В Python операторы присваивания не являются выражениями и, следовательно, не имеют значения. Вместо этого цепные присваивания представляют собой серию операторов с несколькими целями для одного выражения. Задания выполняются слева направо, так что i = arr[i] = f() оценивает выражение f(), затем присваивает результат самой левой цели, i, а затем присваивает тот же результат следующей цели, arr[i], используя новое значение i. [9] По сути это эквивалентно tmp = f(); i = tmp; arr[i] = tmp хотя для временного значения не создается фактическая переменная.

Параллельное назначение

[ редактировать ]

Некоторые языки программирования, такие как APL , Common Lisp , [10] Идти , [11] JavaScript (начиная с версии 1.7), PHP , Maple , Lua , occam 2 , [12] Перл , [13] Питон , [14] РЕБОЛ , Руби , [15] и PowerShell позволяют назначать несколько переменных параллельно, используя такой синтаксис:

a, b := 0, 1

который одновременно присваивает 0 a и от 1 до b. Чаще всего это называют параллельным присваиванием ; оно было введено в CPL в 1963 году под названием « Совместное назначение» . [16] и иногда его называют множественным присвоением , хотя это сбивает с толку при использовании с «одиночным присвоением», поскольку это не противоположности. Если правая часть присваивания представляет собой одну переменную (например, массив или структуру), эта функция называется распаковкой. [17] или деструктурирующее задание : [18]

var list := {0, 1}
a, b := list

Список будет распакован, и ему будет присвоено значение 0. a и от 1 до b. Более того,

a, b := b, a

меняет значения a и b. В языках без параллельного присваивания это пришлось бы писать с использованием временной переменной.

var t := a
a := b
b := t

с a := b; b := a оставляет обоих a и b с исходной стоимостью b.

Некоторые языки, такие как Go , F# и Python , сочетают параллельное присваивание, кортежи и автоматическую распаковку кортежей , чтобы обеспечить возможность возврата нескольких значений из одной функции, как в этом примере Python:

def f():
    return 1, 2
a, b = f()

в то время как другие языки, такие как C# и Rust , показанные здесь, требуют явного построения и деконструкции кортежей с помощью круглых скобок:

// Valid C# or Rust syntax
(a, b) = (b, a);
// C# tuple return
(string, int) f() => ("foo", 1);
var (a, b) = f();
// Rust tuple return
let f = || ("foo", 1);
let (a, b) = f();

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

C# дополнительно допускает обобщенное назначение деконструкции с реализацией, определяемой выражением в правой части, когда компилятор ищет подходящий экземпляр или расширение. Deconstruct метод для выражения, которое должно иметь выходные параметры для присваиваемых переменных. [19] Например, один из таких методов, который бы придавал классу то же поведение, что и возвращаемое значение f() выше было бы

void Deconstruct(out string a, out int b) { a = "foo"; b = 1; }

В C и C++ оператор запятая аналогичен параллельному присваиванию, позволяя выполнять несколько присваиваний в одном операторе. a = 1, b = 2 вместо a, b = 1, 2. В основном это используется в циклах for и заменяется параллельным присваиванием в других языках, таких как Go. [20] Однако приведенный выше код C++ не обеспечивает идеальную одновременность, поскольку правая часть следующего кода a = b, b = a+1 оценивается после левой стороны. В таких языках, как Python, a, b = b, a+1 одновременно назначит две переменные, используя начальное значение a для вычисления нового b.

Присваивание против равенства

[ редактировать ]

Использование знака равенства = как оператор присваивания часто подвергался критике из-за конфликта с равенством при сравнении на равенство. Это приводит как к путанице у новичков при написании кода, так и к путанице даже у опытных программистов при чтении кода. Использование равенства для присваивания восходит к Хайнца Рутисхаузера языку Superplan , разработанному с 1949 по 1951 год, и было особенно популяризировано Фортраном:

Ярким примером плохой идеи был выбор знака равенства для обозначения присваивания. Это восходит к Фортрану в 1957 году. [а] и был слепо скопирован армиями языковых дизайнеров. Почему это плохая идея? Потому что это опровергает вековую традицию, позволяющую «=» обозначать сравнение на равенство, предикат, который может быть либо истинным, либо ложным. Но в Фортране это означало присвоение, обеспечение равенства. В этом случае операнды находятся в неравных отношениях: левый операнд (переменная) должен быть равен правому операнду (выражению). x = y не означает то же самое, что y = x. [21]

Никлаус Вирт , «Хорошие идеи в Зазеркалье»

Начинающие программисты иногда путают присваивание с оператором сравнения , обозначающим равенство, поскольку «=" означает равенство в математике и используется для присваивания во многих языках. Но присваивание изменяет значение переменной, а проверка на равенство проверяет, имеют ли два выражения одинаковое значение.

В некоторых языках, таких как BASIC , один знак равенства ( "=") используется как для оператора присваивания, так и для оператора отношения равенства, при этом контекст определяет, какой из них имеется в виду. В других языках для этих двух операторов используются разные символы. [22] Например:

  • В Алголе и Паскале оператором присваивания является двоеточие и знак равенства ( ":="), в то время как оператор равенства представляет собой одиночное равенство ( "=").
  • В C оператор присваивания представляет собой один знак равенства ( "="), а оператор равенства представляет собой пару знаков равенства ( "==").
  • В R оператор присваивания в основном <-, как в x <- value, но в определенных контекстах можно использовать один знак равенства.

Сходство двух символов может привести к ошибкам, если программист забудет, в какой форме (" =", " ==", " :=") подходит, или опечатка " =" когда " ==". Это распространенная проблема программирования на таких языках, как C (включая одну известную попытку взлома ядра Linux), [23] где оператор присваивания также возвращает присвоенное значение (так же, как функция возвращает значение) и может быть правильно вложен внутри выражений. Если намерением было сравнить два значения в if Например, присваивание с большой вероятностью вернет значение, интерпретируемое как логическое значение true, и в этом случае then будет выполнено, что приведет к неожиданному поведению программы. Некоторые языковые процессоры (например, gcc ) могут обнаруживать такие ситуации и предупреждать программиста о потенциальной ошибке. [24] [25]

Обозначения

[ редактировать ]

Двумя наиболее распространенными представлениями присваивания копирования являются знак равенства ( =) и двоеточие равно ( :=). Обе формы могут семантически обозначать либо оператор присваивания присваивания, либо оператор (который также имеет значение), в зависимости от языка и/или использования.

variable = expression Fortran , PL/I , C его потомки, такие как C++ , Java и т. д.), оболочка Bourne , Python , Go (присвоение предварительно объявленным переменным), R , PowerShell , Nim и т. д.
variable := expression АЛГОЛ (и производные), Simulate , CPL , BCPL , Pascal [26] (и потомки, такие как Modula ), Mary , PL/M , Ada , Smalltalk , Eiffel , [27] [28] Оберон , Дилан , [29] Seed7 , Python (выражение присваивания), [30] Go (сокращение от объявления и определения переменной), [31] Io , AMPL , ML (присваивание эталонному значению), [32] Автохоткей и т. д.

Другие возможности включают стрелку влево или ключевое слово, хотя есть и другие, более редкие варианты:

variable << expression Магия
variable <- expression Ф# , ОКамл , Р , С
variable <<- expression Р
assign("variable", expression) Р
variableexpression АПЛ , [33] Smalltalk , Программирование на языке BASIC
variable =: expression Дж
LET variable = expression БАЗОВЫЙ
let variable := expression XQuery
set variable to expression AppleScript
set variable = expression оболочка C
Set-Variable variable (expression) PowerShell
variable : expression Максима, Максима , К
variable: expression Ребол
var variable expression язык сценариев mIRC
reference-variable :- reference-expression начало

Математические назначения псевдокодов обычно изображаются стрелкой влево.

Некоторые платформы помещают выражение слева, а переменную справа:

MOVE expression TO variable КОБОЛ
expressionvariable ТИ-БЕЙСИК , Касио БЕЙСИК
expression -> variable ПОП-2 , БЕТА , Р
put expression into variable LiveCode
PUT expression IN variable АВС

Некоторые языки, ориентированные на выражения, такие как Lisp. [34] [35] и Tcl единообразно используют префиксный (или постфиксный) синтаксис для всех операторов, включая присваивание.

(setf variable expression) Общий Лисп
(set! variable expression) Схема [36] [37] [38]
set variable expression Ткл
expression variable ! Форт

См. также

[ редактировать ]

Примечания

[ редактировать ]
  1. ^ Использование = предшествует Фортрану, хотя он был популяризирован Фортраном.
  1. ^ Jump up to: а б «2cs24 Декларативный» . www.csc.liv.ac.uk. ​Архивировано из оригинала 24 апреля 2006 года . Проверено 20 апреля 2018 г.
  2. ^ Jump up to: а б с «Императивное программирование» . уа.еду . Архивировано из оригинала 4 марта 2016 года . Проверено 20 апреля 2018 г.
  3. ^ Jump up to: а б с Рюдигер-Маркус Флейг (2008). Программирование биоинформатики на Python: практический курс для начинающих . Вайли-ВЧ. стр. 98–99. ISBN  978-3-527-32094-3 . Проверено 25 декабря 2010 г.
  4. ^ Jump up to: а б с д и Пересекая границы: изучайте функциональное программирование с помощью Haskell. Архивировано 19 ноября 2010 г., в Wayback Machine . Брюсом Тейтом,
  5. ^ Митчелл, Джон К. (2003). Концепции в языках программирования . Издательство Кембриджского университета. п. 23. ISBN  978-0-521-78098-8 . Проверено 3 января 2011 г.
  6. ^ «Императивные языки программирования (IPL)» (PDF) . gwu.edu . Архивировано из оригинала (PDF) 16 июля 2011 г. Проверено 20 апреля 2018 г.
  7. ^ Джон К. Митчелл (2003). Концепции в языках программирования . Издательство Кембриджского университета. стр. 81–82. ISBN  978-0-521-78098-8 . Проверено 3 января 2011 г.
  8. ^ Худак, Пол (2000). Школа экспрессии Haskell: изучение функционального программирования с помощью мультимедиа . Кембридж: Издательство Кембриджского университета. ISBN  0-521-64408-9 .
  9. ^ «7. Простые операторы — документация Python 3.6.5» . docs.python.org . Проверено 20 апреля 2018 г.
  10. ^ «CLHS: Макрос SETF, PSETF» . Общая гиперспецификация Lisp . Лиспворкс . Проверено 23 апреля 2019 г.
  11. ^ Спецификация языка программирования Go: Задания
  12. ^ ИНМОС Лимитед, изд. (1988). Справочное руководство Оккам 2 . Нью-Джерси: Прентис Холл. ISBN  0-13-629312-3 .
  13. ^ Уолл, Ларри ; Кристиансен, Том; Шварц, Рэндал К. (1996). Язык программирования Perl (2-е изд.). Кембридж: О'Рейли. ISBN  1-56592-149-6 .
  14. ^ Лутц, Марк (2001). Язык программирования Python (2-е изд.). Севастополь: О'Рейли. ISBN  0-596-00085-5 .
  15. ^ Томас, Дэвид; Хант, Эндрю (2001). Программирование на Ruby: Руководство прагматичного программиста . Река Аппер-Седл: Эддисон Уэсли. ISBN  0-201-71089-7 .
  16. ^ Д.В. Бэррон и др. , «Основные особенности CPL», Computer Journal 6 :2:140 (1963). полный текст (подписка)
  17. ^ «PEP 3132 — Расширенная итеративная распаковка» . Legacy.python.org . Проверено 20 апреля 2018 г.
  18. ^ «Деструктуризация задания» . Веб-документы MDN . Проверено 20 апреля 2018 г.
  19. ^ «Деконструкция кортежей и других типов» . Документы Майкрософт . Майкрософт . Проверено 29 августа 2019 г.
  20. ^ Эффективный ход : для , «Наконец, в Go нет оператора-запятой, а ++ и -- являются операторами, а не выражениями. Таким образом, если вы хотите запустить несколько переменных в for, вам следует использовать параллельное присваивание (хотя это исключает ++ и --)».
  21. ^ Никлаус Вирт. «Хорошие идеи в Зазеркалье» . CiteSeerX   10.1.1.88.8309 .
  22. ^ «Язык программирования C++. Основы» . ntu.edu.sg. ​01.06.2013 . Проверено 21 июня 2024 г.
  23. ^ Корбет (6 ноября 2003 г.). «Попытка взлома ядра» . lwn.net . Проверено 21 июня 2024 г.
  24. ^ «Параметры статического анализатора (с использованием коллекции компиляторов GNU (GCC))» . gcc.gnu.org . Проверено 21 июня 2024 г.
  25. ^ Дейтел, Пол; Дейтел, Харви (25 октября 2022 г.). «Управляющие операторы C++, часть 2» . Домашние задания . Проверено 21 июня 2024 г.
  26. ^ Мур, Лори (1980). Основы программирования на языке Паскаль . Нью-Йорк: Джон Уайли и сыновья. ISBN  0-470-26939-1 .
  27. ^ Мейер, Бертран (1992). Эйфель Язык . Хемел Хемпстед: Prentice Hall International (Великобритания). ISBN  0-13-247925-7 .
  28. ^ Винер, Ричард (1996). Объектно-ориентированное введение в информатику с использованием Eiffel . Река Аппер-Сэддл, Нью-Джерси: Прентис-Холл. ISBN  0-13-183872-5 .
  29. ^ Фейнберг, Нил; Кин, Соня Э.; Мэтьюз, Роберт О.; Витингтон, П. Такер (1997). Программирование Дилана . Массачусетс: Эддисон Уэсли. ISBN  0-201-47976-1 .
  30. ^ «PEP 572 – Выражения присваивания» . python.org . 28 февраля 2018 года . Проверено 4 марта 2020 г. .
  31. ^ «Спецификация языка программирования Go — Язык программирования Go» . golang.org . Проверено 20 апреля 2018 г.
  32. ^ Уллман, Джеффри Д. (1998). Элементы программирования машинного обучения: издание ML97 . Энглвуд Клиффс, Нью-Джерси: Прентис Холл. ISBN  0-13-790387-1 .
  33. ^ Айверсон, Кеннет Э. (1962). Язык программирования . Джон Уайли и сыновья. ISBN  0-471-43014-5 . Архивировано из оригинала 4 июня 2009 г. Проверено 9 мая 2010 г.
  34. ^ Грэм, Пол (1996). ANSI Common Lisp . Нью-Джерси: Прентис Холл. ISBN  0-13-370875-6 .
  35. ^ Стил, Гай Л. (1990). Common Lisp: язык . Лексингтон: Цифровая пресса. ISBN  1-55558-041-6 .
  36. ^ Дибвиг, Р. Кент (1996). Язык программирования Scheme: ANSI Scheme . Нью-Джерси: Прентис Холл. ISBN  0-13-454646-6 .
  37. ^ Смит, Джерри Д. (1988). Знакомство со схемой . Нью-Джерси: Прентис Холл. ISBN  0-13-496712-7 .
  38. ^ Абельсон, Гарольд; Сассман, Джеральд Джей; Сассман, Джули (1996). Структура и интерпретация компьютерных программ . Нью-Джерси: МакГроу-Хилл. ISBN  0-07-000484-6 .
Arc.Ask3.Ru: конец переведенного документа.
Arc.Ask3.Ru
Номер скриншота №: 1d9ce883e25889547470bd1f435953b7__1721670780
URL1:https://arc.ask3.ru/arc/aa/1d/b7/1d9ce883e25889547470bd1f435953b7.html
Заголовок, (Title) документа по адресу, URL1:
Assignment (computer science) - Wikipedia
Данный printscreen веб страницы (снимок веб страницы, скриншот веб страницы), визуально-программная копия документа расположенного по адресу URL1 и сохраненная в файл, имеет: квалифицированную, усовершенствованную (подтверждены: метки времени, валидность сертификата), открепленную ЭЦП (приложена к данному файлу), что может быть использовано для подтверждения содержания и факта существования документа в этот момент времени. Права на данный скриншот принадлежат администрации Ask3.ru, использование в качестве доказательства только с письменного разрешения правообладателя скриншота. Администрация Ask3.ru не несет ответственности за информацию размещенную на данном скриншоте. Права на прочие зарегистрированные элементы любого права, изображенные на снимках принадлежат их владельцам. Качество перевода предоставляется как есть. Любые претензии, иски не могут быть предъявлены. Если вы не согласны с любым пунктом перечисленным выше, вы не можете использовать данный сайт и информация размещенную на нем (сайте/странице), немедленно покиньте данный сайт. В случае нарушения любого пункта перечисленного выше, штраф 55! (Пятьдесят пять факториал, Денежную единицу (имеющую самостоятельную стоимость) можете выбрать самостоятельно, выплаичвается товарами в течение 7 дней с момента нарушения.)