Как вызвать динамические переменные из состояния в React? [Дубликат]

Когда я столкнулся с этой ошибкой в ​​Visual Studio,

«При установлении соединения с SQL Server возникла связанная с сетью или конкретная ошибка экземпляра. Сервер не найден или не был доступен. Проверьте правильность имени экземпляра и настройте SQL Server для удаленного подключения. (поставщик: поставщик Named Pipes, ошибка: 40 - не удалось открыть соединение с SQL Server) »

... это было во время выполнения следующего кода C #, который пытался получите данные SQL Server, чтобы отобразить их в сетке. Разрыв произошел именно в строке, которая говорит connect.Open ():

        using (var connect = Connections.mySqlConnection)
        {
            const string query = "SELECT Name, Birthdate, Narrative FROM Friends";
            using (var command = new SqlCommand(query, connect))
            {
                connect.Open();
                using (var dr = command.ExecuteReader())
                {
                    while (dr.Read())
                    {
                        // blah
                    }
                }
            }
        }

Это было необъяснимо, потому что SQL-запрос был очень простым, у меня была правильная строка подключения, и сервер базы данных был доступен. Я решил запустить сам SQL-запрос вручную в SQL Management Studio, и он прошел отлично и дал несколько записей. Но в результатах запроса оставалось одно: в тексте типа «varchar (max) в таблице« Друзья »был некорректно закодированный текст HTML (в частности, некоторые закодированные символы комментариев сортировки <!--, помещенные в данные столбца« Повествование » ). Строка подозрительных данных выглядела так:

Name    Birthdate    Narrative
====    =========    ============== 
Fred    21-Oct-79    &lt;!--HTML Comment -->Once upon a time...

Обратите внимание на кодированный HTML-символ «&lt;», который означал «& lt;» персонаж. Как-то это пробилось в базу данных, и мой код на C # не смог его забрать! Он провалился каждый раз прямо на линии connect.Open ()! После того, как я вручную отредактировал эту одну строку данных в таблице базы данных «Друзья» и поместил в декодированный «& lt;» характер, все сработало! Вот как должна выглядеть эта строка:

Name    Birthdate    Narrative
====    =========    ============== 
Fred    21-Oct-79    <!--HTML Comment -->Once upon a time...

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

UPDATE Friends SET Narrative = '<!--HTML Comment -->Once upon a time...' WHERE Narrative LIKE '&lt%'

Итак, мораль истории (по крайней мере, в моем случае) , дезинфицируйте свой HTML-контент, прежде чем хранить его в базе данных, и вы не получите эту загадочную ошибку SQL Server в первую очередь! (Ну, правильная дезинфекция / декодирование вашего HTML-контента является предметом другого обсуждения, достойного отдельного поиска StackOverflow, если вам нужна дополнительная информация!) [/ ​​G6]

516
задан Taryn 22 March 2017 в 17:12
поделиться

14 ответов

Существует два способа доступа к свойствам объекта:

  • Точечная нотация: something.bar
  • Обозначение скобок: something['bar']

Значение между скобками может быть любым выражением. Поэтому, если имя свойства хранится в переменной, вы должны использовать нотацию в виде скобок:

var foo = 'bar';
something[foo];
// both x = something[foo] and something[foo] = x work as expected
652
ответ дан Salman A 18 August 2018 в 22:07
поделиться
  • 1
    осторожно с этим: javascript компиляторы будут здесь ошибки, поскольку они не переименовывают строки, но они переименовывают свойства объекта – chacham15 6 December 2011 в 10:40
  • 2
    Более подробная информация о том, почему это возможно: объекты JS являются ассоциативными массивами, поэтому. Дальнейшее чтение: quirksmode.org/js/associative.html stackoverflow.com/questions/14031368/… – dotnetguy 3 June 2014 в 10:00
  • 3
    @dotnetguy Нет, они не являются. Массивы - это объекты, которые наследуются от прототипа простого JS-объекта, и поэтому вы можете добавлять свойства go-go, как любой простой объект. «Ассоциативное» поведение более похоже на объект, чем массив. Вы не можете перебирать «ассоциативную» версию простым индексом, чтобы не отображать поведение, подобное массиву. Вы можете определить свой «ассоциативный» массив как {} или [] и относиться к нему одинаково в любом случае в случае случайного доступа к свойствам. – Vanquished Wombat 3 January 2017 в 17:01
  • 4
    @VanquishedWombat Не знаете, к чему относится ваше возражение? Я не сказал, что объекты JS являются массивами? – dotnetguy 6 January 2017 в 01:30
  • 5
    как ссылка на правильный ответ, Ссылка – youhana 8 June 2017 в 21:23

Ниже приведен метод получения свойства или вложенного объекта из объекта с использованием нотации пути. Это адаптация аналогичного вопроса, заданного «Prusprus» в 2014 году.

У меня есть файл конфигурации с вложенными массивами и вы хотите получить доступ к данным с веб-страницы, отправив путь в form:

"unit_cfg [2] .chn_cfg [7] .chn_type"

Эта функция вернет одно свойство или объект. Да, это можно упростить ...

function fetchFromObject(obj: Object, path: string): boolean | Object {
var dot_idx: number;
var lbkt_idx: number;
var rbkt_idx: number;
var prop: string;
var prop_idx: number;
var new_obj: Object;
var new_path: string;

// Return if no object.
if (typeof obj === 'undefined') {
    return false;
}

// Get index of first left bracket in path.
lbkt_idx = path.indexOf('[');
// If left bracket.
if (lbkt_idx > -1) {
    // Get right bracket index.
    rbkt_idx = path.indexOf(']');
}
// Get index of first dot in path.
dot_idx = path.indexOf('.');

/*
 * Most complicated situation is if there are both brackets
 * and dots in the path. This means we have a mixture of both
 * indexed and non-indexed properties:
 *
 *      x[].y --or-- x.y[]
 *
 * In this case, we must see if the indexed property is before
 * or after the non-indexed property.
 *
 * In either case, we must recurse.
 */
if ((lbkt_idx > -1) && (dot_idx > -1)) {
    // If bracket is before dot: x[].y
    if (lbkt_idx < dot_idx) {
        // Get property string.
        prop = path.substr(0, lbkt_idx);
        // Get index.
        prop_idx = Number(path.substring(lbkt_idx + 1, rbkt_idx));
        // Get path to right of dot.
        new_path = path.substr(dot_idx + 1);
        // Get new object.
        new_obj = obj[prop][prop_idx];
        // Recurse.
        return fetchFromObject(new_obj, new_path);
    }
    // Else dot before bracket: x.y[]
    else {
        // Get property string.
        prop = path.substr(0, dot_idx);
        // Get path to right of dot.
        new_path = path.substr(dot_idx + 1);
        // Get new object.
        new_obj = obj[prop];
        // Recurse.
        return fetchFromObject(new_obj, new_path);
    }
}
/*
 * Else recurse if dotted property; x.y
 */
else if (dot_idx > -1) {
    // Get property string.
    prop = path.substr(0, dot_idx);
    // Get path to right of dot.
    new_path = path.substr(dot_idx + 1);
    // Get new object.
    new_obj = obj[prop];
    // Recurse.
    return fetchFromObject(new_obj, new_path);
}
/*
 * Else done if single indexed property: x[]
 */
else if (lbkt_idx > -1) {
    // Get property string.
    prop = path.substr(0, lbkt_idx);
    // Get index.
    prop_idx = Number(path.substring(lbkt_idx + 1, rbkt_idx));
    // Return with object.
    return obj[prop][prop_idx];
}
/*
 * Else single non-indexed property.
 */
return obj[path];

}

-6
ответ дан bobwirka 18 August 2018 в 22:07
поделиться
  • 1
    Мне нравится этот ответ, потому что использование foo ['bar'] является излишним, это намного проще – Robert Pounder 4 July 2017 в 15:53
  • 2
    Это даже не похоже на JavaScript ... – Angel Politis 17 August 2018 в 07:11
const something = { bar: "Foobar!" };
const foo = 'bar';

something[\`${foo}\`];
-4
ответ дан Cody Gray 18 August 2018 в 22:07
поделиться
  • 1
    Почему бы вам это сделать? Ваш foo уже является строкой, поэтому `${foo}` в точности совпадает с foo. (Кроме того, ваш код, похоже, имеет некоторые дополнительные обратные косые черты, которые там не принадлежат. Но это все равно будет бессмысленным, даже если вы исправили эту синтаксическую ошибку.) – Ilmari Karonen 19 September 2017 в 18:49

Это мое решение:

function resolve(path, obj) {
    return path.split('.').reduce(function(prev, curr) {
        return prev ? prev[curr] : null
    }, obj || self)
}

Примеры использования:

resolve("document.body.style.width")
// or
resolve("style.width", document.body)
// or even use array indexes
// (someObject has been defined in the question)
resolve("part.0.size", someObject) 
// returns null when intermediate properties are not defined:
resolve('properties.that.do.not.exist', {hello:'world'})
36
ответ дан GeekyDeaks 18 August 2018 в 22:07
поделиться

Вы можете достичь этого несколькими способами.

let foo = {
    bar: 'Hello World'
};

foo.bar;
foo['bar'];

Обозначение скобок особенно мощно, так как оно позволяет вам получить доступ к свойству на основе переменной:

let foo = {
    bar: 'Hello World'
};

let prop = 'bar';

foo[prop];

Это может быть расширено до циклизации по каждому свойству объекта. Это может казаться излишним из-за новых конструкций JavaScript, таких как ... из ..., но помогает иллюстрировать прецедент:

let foo = {
    bar: 'Hello World',
    baz: 'How are you doing?',
    last: 'Quite alright'
};

for (let prop in foo.getOwnPropertyNames()) {
    console.log(foo[prop]);
}

Оба точечных и скобковых обозначения также работают как ожидалось для вложенных объектов :

let foo = {
    bar: {
        baz: 'Hello World'
    }
};

foo.bar.baz;
foo['bar']['baz'];
foo.bar['baz'];
foo['bar'].baz;

Деструктурирование объекта

Мы могли бы также рассмотреть разрушение объекта как средство доступа к свойству в объекте, но следующим образом:

let foo = {
    bar: 'Hello World',
    baz: 'How are you doing?',
    last: 'Quite alright'
};

let prop = 'last';
let { bar, baz, [prop]: customName } = foo;

// bar = 'Hello World'
// baz = 'How are you doing?'
// customName = 'Quite alright'
12
ответ дан Gorka Hernandez 18 August 2018 в 22:07
поделиться

Интересно, когда вам нужно передать параметры этой функции.

Код jsfiddle

var obj = {method:function(p1,p2,p3){console.log("method:",arguments)}}

var str = "method('p1', 'p2', 'p3');"

var match = str.match(/^\s*(\S+)\((.*)\);\s*$/);

var func = match[1]
var parameters = match[2].split(',');
for(var i = 0; i < parameters.length; ++i) {
  // clean up param begninning
    parameters[i] = parameters[i].replace(/^\s*['"]?/,'');
  // clean up param end
  parameters[i] = parameters[i].replace(/['"]?\s*$/,'');
}

obj[func](parameters); // sends parameters as array
obj[func].apply(this, parameters); // sends parameters as individual values
1
ответ дан Jacksonkr 18 August 2018 в 22:07
поделиться

Всякий раз, когда вам нужно динамически обращаться к ресурсу, вы должны использовать квадратную скобку для доступа к свойству, а не «.». оператор Синтаксис: object [propery}

const something = { bar: "Foobar!" };
const foo = 'bar';
// something.foo; -- not correct way at it is expecting foo as proprty in  something={ foo: "value"};
// correct way is  something[foo]
alert( something[foo])

2
ответ дан Manasi 18 August 2018 в 22:07
поделиться

ОБНОВЛЕНО

Я принял во внимание комментарии и согласился. Eval следует избегать.

Доступ к свойствам корня в объекте легко достигается с помощью obj[variable], но получение вложенных усложняет ситуацию.

Пример

// Accessing root property
var rootProp = 'rootPropert';
_.get(object, rootProp, defaultValue);

// Accessing nested property
var listOfNestedProperties = [var1, var2];
_.get(object, listOfNestedProperties);

Lodash get может использоваться по-разному, вот ссылка на документацию lodash.get

3
ответ дан Mr Br 18 August 2018 в 22:07
поделиться
  • 1
    Лучше избегать использования eval, когда это возможно. [Д0] stackoverflow.com/questions/86513/… – Luke 23 June 2015 в 18:07
  • 2
    Использование eval для чего-то столь же тривиального, как и для доступа к свойствам, является простым излишеством и вряд ли целесообразно при любых обстоятельствах. Что такое «проблема»? obj['nested']['test'] работает очень хорошо и не требует, чтобы вы вставляли код в строки. – Paul Stenne 23 October 2015 в 10:14
  • 3
    eval в три раза медленнее или больше, я бы не рекомендовал это новичкам, потому что он мог бы научить их вредным привычкам. Я использую obj['nested']['value'] - помните детей, eval - зло! – jaggedsoft 26 November 2015 в 02:25
  • 4
    @Luke Он теперь единственный, кто хочет привести Лодаша _.get к столу. Я думаю, что этот ответ заслуживает теперь upvotes вместо downvotes. Это может быть излишним, но хорошо знать, что он существует. – Emile Bergeron 20 December 2016 в 22:42
  • 5
    Благодарим вас за введение lodash для этого. Я пришел сюда через google, ища метод для определения значения в объекте и использовал свой метод _.set (который идентичен выше, но с дополнительным аргументом для заданного значения). – TPHughes 3 July 2018 в 09:03

Вы должны использовать JSON.parse, посмотрите https://www.w3schools.com/js/js_json_parse.asp

const obj = JSON.parse('{ "name":"John", "age":30, "city":"New York"}')
console.log(obj.name)
console.log(obj.age)
-2
ответ дан onmyway133 18 August 2018 в 22:07
поделиться

В javascript мы можем получить доступ с помощью:

  • точечной нотации - foo.bar
  • квадратных скобок - foo[someVar] или foo["string"]

Но только второй случай позволяет динамически обращаться к свойствам:

var foo = { pName1 : 1, pName2 : [1, {foo : bar }, 3] , ...}

var name = "pName"
var num  = 1;

foo[name + num]; // 1

// -- 

var a = 2;
var b = 1;
var c = "foo";

foo[name + a][b][c]; // bar
26
ответ дан Sonique 18 August 2018 в 22:07
поделиться
  • 1
    Я смотрю на 2000 строк операторов if, потому что предыдущий разработчик не использовал квадратные скобки и статически доступные свойства объекта с помощью точечной нотации. Это приложение для утверждения, которое имеет 7 разных утвердителей, и все шаги одинаковы. /Покойся с миром – Chad 7 June 2018 в 14:28

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

var suffix = " name";

var person = {
    ["first" + suffix]: "Nicholas",
    ["last" + suffix]: "Zakas"
};

console.log(person["first name"]);      // "Nicholas"
console.log(person["last name"]);       // "Zakas"

Это называется именами вычисленных свойств

15
ответ дан try-catch-finally 18 August 2018 в 22:07
поделиться
0
ответ дан JJJ 7 September 2018 в 05:47
поделиться
-1
ответ дан T.Todua 30 October 2018 в 09:58
поделиться
1
ответ дан JJJ 30 October 2018 в 09:58
поделиться
Другие вопросы по тегам:

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