часто используемый редко определяемые условия: lvalue

Мне нужна была какая-то логика форматирования для совместного использования несколькими компонентами, а также, как разработчик Angular, естественно, склонялся к службе.

Я разделил логику, поместив ее в отдельный файл

function format(input) {
    //convert input to output
    return output;
}

module.exports = {
    format: format
};

, а затем импортировал его как модуль

import formatter from '../services/formatter.service';

//then in component

    render() {

        return formatter.format(this.props.data);
    }
20
задан Sinan Ünür 21 September 2009 в 04:54
поделиться

7 ответов

lvalue является значением, которому можно присвоить:

lvalue = rvalue;

Это коротко для "левого значения" или "левого значения", и это - в основном просто значение на , уехал из эти = знак, т.е. значение, которому Вы присваиваете что-то.

Как пример того, что не lvalue (т.е. только rvalue):

printf("Hello, world!\n") = 100; // WTF?

, Что код не работает, потому что printf() (функция, которая возвращается int) не может быть lvalue, только rvalue.

27
ответ дан 29 November 2019 в 22:50
поделиться

Одно из лучших объяснений, о которых я знаю, может быть найдено в эта статья о ссылках RValue .

другой способ определить, является ли выражение lvalue, состоит в том, чтобы попросить, чтобы "я мог взять его адрес?". Если Вы можете, это быть lvalue. Если Вы не можете, это быть rvalue. Например, & obj, & *ptr, & ptr [индекс] и & ++ x все допустимы (даже при том, что некоторые из тех выражений глупы), в то время как & 1729, & (x + y), & станд.:: строка ("мяуканье") и & x ++ все недопустимы. Почему это работает? Операция вычисления адреса требует, чтобы ее "операнд должен быть lvalue" (C++ 03 5.3.1/2). Почему это требует этого? Взятие адреса постоянного объекта прекрасно, но взятие адреса временного файла было бы чрезвычайно опасно, потому что временные файлы испаряются быстро.

8
ответ дан 29 November 2019 в 22:50
поделиться

Что-то, что появляется на левой стороне присвоения т.е. чего-то, чему можно присвоить.

Примечание, что в C++ вызов функции может быть lvalue если:

int & func() {
   static int a = 0;
   return a;
}

затем:

func() = 42;     // is legal (and not uncommon)
12
ответ дан 29 November 2019 в 22:50
поделиться

Это - традиционно левая сторона "=" оператор. Однако со временем, значением "lvalue" / "rvalue" измененный. C++ добавил термин "немодифицируемого lvalue", который является любым lvalue, который не может присвоенный: массивы и переменные, которые квалифицированы с "константой", являются двумя примерами. В C Вы не можете присвоить никакому rvalue (см. ниже). Аналогично, в C++, Вы не можете присвоиться к rvalues, которые не имеют некоторого определяемого пользователем типа класса.

можно сказать, что "lvalue" является выражением, которое называет объект, который сохраняется со временем и занимает некоторое местоположение устройства хранения данных. Можно ли присвоить тому выражению, не важно для той классификации. Ссылка, в частности, является также lvalue, потому что она имеет имя, которое сохраняется со временем. Все следующее является lvalues, потому что они все обращаются к именованным объектам. Также обратите внимание, что const не имеет никакого эффекта на lvalue-мыс.

int a; lvalue: a;
       lvalue: ++a;
int a[2]; lvalue: a;
int &ra = a; lvalue: ra;
int *pa = &a; lvalue: *pa;

термин "rvalue" используется для вещей как литералы и значения перечислителя и для временных файлов, которые не обладают забавой наличия долгой жизни и уничтожаются сразу же в конце полного выражения. Для rvalues не аспект персистентности важен, но аспект значения. Функции в C++ являются lvalues, потому что они являются персистентными, и у них есть адрес, даже при том, что они не объекты. Я пропустил их в вышеупомянутом обзоре lvalues, потому что легче схватить lvalues, сначала только принимая объекты во внимание. Все следующее является rvalues:

enum { FOO, BAR }; rvalue: BAR;
int a[2]; rvalue: (a+1);
rvalue: 42;
int a; rvalue: a++; // refering to a temporary
struct mystruct { }; mystruct f() { return mystruct(); } rvalue: f();

Кстати, часто у Вас есть lvalue, но для оператора нужен rvalue. Например, двоичный файл, встроенный "+" оператор, добавляет два значения. lvalue выражение сначала и для всех указывает местоположение, где значение сначала должно быть считано. Таким образом, когда Вы добавляете, что две переменные, "lvalue к rvalue" преобразование происходит. В Стандарте говорится, что значение, содержавшееся в lvalue выражении, является своим результатом rvalue:

int a = 0, b = 1;
int c = a + b; // read values out of the lvalues of a and b. 

Другие операторы не берут rvalue, но lvalues. Они не читают значение. Примером является операция вычисления адреса, &. Вы не можете взять адрес rvalue выражения. Некоторые rvalues даже не являются объектами: Они не занимают устройства хранения данных. Примеры снова, литералы (10, 3.3...) и значения перечислителя.

, Как тот страшный материал полезен?

Хорошо это имеет несколько преимуществ, чтобы иметь различие lvalue и rvalue

  • , Позволяющего компилятор опустить брать устройство хранения данных для rvalues и использовать регистры/постоянную память для скалярных величин
  • Отмечающие выражения как неуловимые: rvalues не будет жить долго
    • , Позволяет эффективную семантику копии для компилятора внутренне и в C++ 1x также выставленный программисту (см. семантику перемещения и rvalue ссылки): Мы можем ускользать ресурсы от rvalues, которые будут уничтоженными так или иначе.
  • Позволяет создавать правила на том свойстве
    • rvalues, не позволяются быть сгенерированным от еще неинициализированные объекты, где lvalues относится к. Но lvalues может относиться к неинициализированным объектам очень хорошо
    • , rvalues никогда не может быть полиморфным. Их статический тип должен также быть их динамическим типом: Упрощает правила для оператора идентификатора типа.

... Существует больше к нему, я чувствую это...

12
ответ дан 29 November 2019 в 22:50
поделиться

"L" в lvalue обычно описывается как обозначающий "местоположение". lvalue указывает местоположение чего-то; как другая отвечающая сторона, на которую указывают, lvalues можно было обычно брать их адрес. Поэтому числовые литералы и нессылочные функциональные возвращаемые значения не являются lvalues.

L раньше обозначал "левый", пока константа не была введена в C++. Константа lvalues не может появиться на левой стороне присвоения.

2
ответ дан 29 November 2019 в 22:50
поделиться

Простой пример того, что является определенно не lvalue:

3 = 42;
0
ответ дан 29 November 2019 в 22:50
поделиться

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

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

  • тип массива
  • неполный тип
  • квалифицированный к константе тип
  • объект является структурой или типом объединения, и у одного из его участников есть квалифицированный к константе тип

, поскольку эти lvalues не являются модифицируемыми, они не могут появиться на левой стороне оператора присваивания.

В C++, вызов функции, который возвращает ссылку, является lvalue. Иначе вызов функции является rvalue выражением. В C++ каждое выражение производит lvalue, rvalue или никакое значение.

операторы Certain требуют lvalues для некоторых их операндов. Таблица ниже приводит эти операторы и дополнительные ограничения на их использование.

     Operator                          Requirement
     & (unary)                         Operand must be an lvalue.
     ++ --                             Operand must be an lvalue.
                                          This applies to both prefix
                                            and postfix forms.
     = += -= *= %= >= &= ^= |=         Left operand must be an lvalue.

, Например, все операторы присваивания оценивают свой правильный операнд и присваивают то значение их левому операнду. Левый операнд должен быть модифицируемым lvalue или ссылкой на модифицируемый объект.

операция взятия адреса (&) требует lvalue как операнда, в то время как инкремент (++) и декремент (-) операторы требует модифицируемого lvalue как операнда.

0
ответ дан 29 November 2019 в 22:50
поделиться
Другие вопросы по тегам:

Похожие вопросы: