Вытащить данные из JSON

xoffer

Client
Регистрация
27.01.2011
Сообщения
88
Благодарностей
8
Баллы
8
Есть кусок JSON
C#:
{"ProductAttributeCatalog:18":{"id":18,"name":"Производитель","value":"Kirkland","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:228":{"id":228,"name":"Страна производитель","value":"Израиль","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3855":{"id":3855,"name":"Тип кожи головы","value":"Все типы кожи","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3830":{"id":3830,"name":"Тип волос","value":"Склонные к выпадению, Все типы волос","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3230":{"id":3230,"name":"Классификация косметического средства","value":"Лечебная (Космецевтика)","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:128":{"id":128,"name":"Объем","value":"60 мл","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3770":{"id":3770,"name":"Гипоаллергенно","value":"Да","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3875":{"id":3875,"name":"Назначение средства для волос","value":"Улучшение роста волос, Восстановление, Оздоровление кутикулы, Оздоровление, От выпадения","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3216":{"id":3216,"name":"Упаковка средства","value":"Флакон с дозатором","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3902":{"id":3902,"name":"Проблема волос и кожи головы","value":"Выпадение волос, Ослабленный рост волос, Истонченные волосы","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:1315":{"id":1315,"name":"Пол","value":"Унисекс","group":"Основные","__typename":"ProductAttributeCatalog"},"ProductAttributeCatalog:3993":{"id":3993,"name":"Консистенция средства","value":"Жидкая","group":"Основные","__typename":"ProductAttributeCatalog"}}
Нужно вытащить только данные пар name и value . Через парсинг json чет не получается. Код разбирается, но вот как выбрать эти данные не пойму, т.к. меняется номер в ProductAttributeCatalog.
 

volody00

Client
Регистрация
06.09.2016
Сообщения
918
Благодарностей
953
Баллы
93
регулярками можешь. F3 для открытия конструктора регулярных выражений
 

Alexmd

Client
Регистрация
10.12.2018
Сообщения
1 022
Благодарностей
1 424
Баллы
113
Куда вытащить - непонятно. Так что заполним необходимыми данными тестовую табличку с именем "data", которая, соответственно, должна быть добавлена в проект.
C#:
foreach(string s in project.Json.GetMembersList()){
    project.Tables["data"].AddRow(new string[]{
        s.Split(':').Last(),
        project.Json.GetMember(s).name,
        project.Json.GetMember(s).value
    });   
}
 
  • Спасибо
Реакции: xoffer и volody00

Hartwell

Client
Регистрация
25.09.2014
Сообщения
194
Благодарностей
118
Баллы
43
Вариант #1
C#:
string jsoninput = "...";
Newtonsoft.Json.Linq.JObject jResp = Newtonsoft.Json.Linq.JObject.Parse(jsoninput);
    var itemsList = from ord in jResp.Children().Children()
    select ord;
              
foreach (var item in itemsList)
{
   Console.WriteLine(item.ToString());
}

/*
На выходе foreach нарисует такие json, которые не составит труда распасить... я надеюсь...
{
  "id": 18,
  "name": "Производитель",
  "value": "Kirkland",
  "group": "Основные",
  "__typename": "ProductAttributeCatalog"
}
{
  "id": 228,
  "name": "Страна производитель",
  "value": "Израиль",
  "group": "Основные",
  "__typename": "ProductAttributeCatalog"
}
*/

Вариант #2
лень накидывать (ну и он не под эту таску, но подход общий)

C#:
Regex regex = new Regex(...);  // регулярка для поиска key, лень заполнять, типо того ProductAttributeCatalog:\d+
JObject json = JObject.Parse(text);
foreach (var property in json.Properties()) // перебираем проперти
{
    if (regex.IsMatch(property.Name))  // ищем совпадения регулярки среди Key/Имен значений json. Если Match то выполняем дальше
    {
        ...
    }
}
подробнее тут https://www.newtonsoft.com/json/help/html/RegexQuery.htm

есть еще один вариант, но думаю и двух достаточно, без плясок вокруг бесколёсного велосипеда, в виде "распарсь просто регулярками" =)) ) Тут регулярки в рамках json содержимого, ну вообщем кому надо тот поймет)
 
Последнее редактирование:

Carty

Client
Регистрация
16.06.2021
Сообщения
39
Благодарностей
68
Баллы
18
Тоже самое, что и у @Hartwell, но чуть красивше :-)
C#:
var j = JObject.Parse("{'ProductAttributeCatalog:18':{'id':18,'name':'Производитель','value':'Kirkland','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:228':{'id':228,'name':'Страна производитель','value':'Израиль','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3855':{'id':3855,'name':'Тип кожи головы','value':'Все типы кожи','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3830':{'id':3830,'name':'Тип волос','value':'Склонные к выпадению, Все типы волос','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3230':{'id':3230,'name':'Классификация косметического средства','value':'Лечебная (Космецевтика)','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:128':{'id':128,'name':'Объем','value':'60 мл','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3770':{'id':3770,'name':'Гипоаллергенно','value':'Да','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3875':{'id':3875,'name':'Назначение средства для волос','value':'Улучшение роста волос, Восстановление, Оздоровление кутикулы, Оздоровление, От выпадения','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3216':{'id':3216,'name':'Упаковка средства','value':'Флакон с дозатором','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3902':{'id':3902,'name':'Проблема волос и кожи головы','value':'Выпадение волос, Ослабленный рост волос, Истонченные волосы','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:1315':{'id':1315,'name':'Пол','value':'Унисекс','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3993':{'id':3993,'name':'Консистенция средства','value':'Жидкая','group':'Основные','__typename':'ProductAttributeCatalog'}}");

var props = j.Properties()
    .Where(p => p.Name.StartsWith("ProductAttributeCatalog"))
    .Select(p => p.Value)
    .Select(p => ((string)p["name"], (string)p["value"]));

foreach(var prop in props)
{
    Console.WriteLine($"{prop.Item1}: {prop.Item2}");
}
 
  • Спасибо
Реакции: Hartwell

Hartwell

Client
Регистрация
25.09.2014
Сообщения
194
Благодарностей
118
Баллы
43
Тоже самое, что и у @Hartwell, но чуть красивше :-)
upd - либо ты обновил ответ, либо пора спать, вроде был другой код) ну да ладно не суть.


Второй так для полета фантазии.. а ты на первый посмотри))
Магия в одной строке... 8-)

C#:
var itemsList = from ord in jResp.Children().Children()
    select ord;
Но второй вариант (который и у тебя) все же более универсальный, ибо в том что #1 - вложенность Keys должна быть строго на одном уровне (либо это уже будет не так изящно).
Задачи не унифицировать (а жаль), так что крутимся исходя из условий таски и пытаемся найти компромисс между подходами к решению. :bg:
 

Carty

Client
Регистрация
16.06.2021
Сообщения
39
Благодарностей
68
Баллы
18
Задачи не унифицировать (а жаль), так что крутимся исходя из условий таски и пытаемся найти компромисс между подходами к решению.
Что ж, можно пойти и дальше, "магия в одной строке" (почти, если убрать переводы на новую строку) с проверкой на нужный ключ и готовым объектом на выходе. Кто кого?)
(Но я бы лично так делать не стал, т.к. считаю использование dynamic плохой идеей)
C#:
var j = JObject.Parse("{'ProductAttributeCatalog:18':{'id':18,'name':'Производитель','value':'Kirkland','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:228':{'id':228,'name':'Страна производитель','value':'Израиль','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3855':{'id':3855,'name':'Тип кожи головы','value':'Все типы кожи','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3830':{'id':3830,'name':'Тип волос','value':'Склонные к выпадению, Все типы волос','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3230':{'id':3230,'name':'Классификация косметического средства','value':'Лечебная (Космецевтика)','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:128':{'id':128,'name':'Объем','value':'60 мл','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3770':{'id':3770,'name':'Гипоаллергенно','value':'Да','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3875':{'id':3875,'name':'Назначение средства для волос','value':'Улучшение роста волос, Восстановление, Оздоровление кутикулы, Оздоровление, От выпадения','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3216':{'id':3216,'name':'Упаковка средства','value':'Флакон с дозатором','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3902':{'id':3902,'name':'Проблема волос и кожи головы','value':'Выпадение волос, Ослабленный рост волос, Истонченные волосы','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:1315':{'id':1315,'name':'Пол','value':'Унисекс','group':'Основные','__typename':'ProductAttributeCatalog'},'ProductAttributeCatalog:3993':{'id':3993,'name':'Консистенция средства','value':'Жидкая','group':'Основные','__typename':'ProductAttributeCatalog'}}");

var props = from p in j.Properties()
    where p.Name.StartsWith("ProductAttributeCatalog")
    select (dynamic)p.Value;

foreach(var prop in props)
{
    Console.WriteLine($"{prop.name}: {prop.value}");
}

Можно, конечно, и через SelectToken, но уж больно это дело страшно и нечитаемо выглядит
 

xoffer

Client
Регистрация
27.01.2011
Сообщения
88
Благодарностей
8
Баллы
8
Всем спасибо за ответы). Первый код отрабатывает, как мне надо и куда надо (в таблицу), просто не написал это в вопросе. Остальные не стал проверять.
 

Markoonij

Client
Регистрация
13.10.2020
Сообщения
70
Благодарностей
3
Баллы
8
Ребята, помогите разобраться. Имею JSON:

JavaScript:
{
  "historyCoupons": [
    {
      "couponRef": 4118671190,
      "couponExternalRef": "368ea9e5-f77c-43ff-8b8a-a766c1ebb04a",
      "placedDate": "2021-11-04T23:57:08.979Z",
      "currency": "GBP",
      "channel": "WEB",
      "tags": [],
      "bets": [
        {
          "betRef": 6439831678,
          "couponRowIndexes": [
            0
          ],
          "betOdds": 1870,
          "playedOdds": 1870,
          "betStatus": "WON",
          "stake": 7000,
          "payout": 13090,
          "potentialPayout": 13090,
          "tags": []
        }
      ],
      "outcomes": [
        {
          "outcomeId": 3003640339,
          "eventId": 1018213803,
          "betOfferId": 2289099572,
          "label": "Under 21.5",
          "settledInfo": {
            "result": {
              "score": "13-8",
              "correct": [
                "Under 21.5"
              ],
              "scratched": []
            }
          },
          "status": "WON",
          "outcomeTags": []
        }
      ],
      "couponRows": [
        {
          "index": 0,
          "outcomeId": 3003640339,
          "status": "WON",
          "playedOdds": 1870,
          "payoutOdds": 1870,
          "bestOddsGuaranteed": false,
          "tags": [],
          "selectionType": "SIMPLE"
        }
      ],
      "events": [
        {
          "eventId": 1018213803,
          "homeName": "Griekspoor, Tallon",
          "awayName": "Celikbilek, Altug",
          "eventName": "Griekspoor, Tallon - Celikbilek, Altug",
          "eventGroups": [
            {
              "id": 1000093193,
              "name": "Tennis"
            },
            {
              "id": 1000093377,
              "name": "Challenger"
            },
            {
              "id": 2010132056,
              "name": "Tenerife"
            }
          ],
          "eventStartDate": "2021-11-05T11:00:00Z"
        }
      ],
      "betOffers": [
        {
          "betOfferId": 2289099572,
          "boType": "Over/Under",
          "boTypeId": 6,
          "criterion": "Total Games",
          "line": 21500,
          "tags": []
        }
      ]
    },
     {
      "couponRef": 4118652116,
      "couponExternalRef": "1612afab-3001-4941-9363-dba6d7e1c626",
      "placedDate": "2021-11-04T23:53:58.952Z",
      "currency": "GBP",
      "channel": "WEB",
      "tags": [],
      "bets": [
        {
          "betRef": 6439798882,
          "couponRowIndexes": [
            0
          ],
          "betOdds": 2120,
          "playedOdds": 2120,
          "betStatus": "WON",
          "stake": 7000,
          "payout": 14840,
          "potentialPayout": 14840,
          "tags": []
        }
      ],
      "outcomes": [
        {
          "outcomeId": 3003640388,
          "eventId": 1018213803,
          "betOfferId": 2289099590,
          "label": "Griekspoor, Tallon -4.5",
          "settledInfo": {
            "result": {
              "score": "13-8",
              "correct": [
                "Griekspoor, Tallon -4.5"
              ],
              "scratched": []
            }
          },
          "status": "WON",
          "participantId": 1002123604,
          "outcomeTags": []
        }
      ],
      "couponRows": [
        {
          "index": 0,
          "outcomeId": 3003640388,
          "status": "WON",
          "playedOdds": 2120,
          "payoutOdds": 2120,
          "bestOddsGuaranteed": false,
          "tags": [],
          "selectionType": "SIMPLE"
        }
      ],
      "events": [
        {
          "eventId": 1018213803,
          "homeName": "Griekspoor, Tallon",
          "awayName": "Celikbilek, Altug",
          "eventName": "Griekspoor, Tallon - Celikbilek, Altug",
          "eventGroups": [
            {
              "id": 1000093193,
              "name": "Tennis"
            },
            {
              "id": 1000093377,
              "name": "Challenger"
            },
            {
              "id": 2010132056,
              "name": "Tenerife"
            }
          ],
          "eventStartDate": "2021-11-05T11:00:00Z"
        }
      ],
      "betOffers": [
        {
          "betOfferId": 2289099590,
          "boType": "Handicap",
          "boTypeId": 1,
          "criterion": "Game Handicap",
          "line": -4500,
          "tags": []
        }
      ]
    },
    {
      "couponRef": 4118673248,
      "couponExternalRef": "0a85254e-ebef-481d-9b51-df998c05e02c",
      "placedDate": "2021-11-05T23:43:54.288Z",
      "currency": "GBP",
      "channel": "WEB",
      "tags": [],
      "bets": [
        {
          "betRef": 6439802468,
          "couponRowIndexes": [
            0
          ],
          "betOdds": 0,
          "playedOdds": 1960,
          "betStatus": "LOST",
          "stake": 7000,
          "payout": 0,
          "potentialPayout": 0,
          "tags": []
        }
      ],
      "outcomes": [
        {
          "outcomeId": 3003576483,
          "eventId": 1008151189,
          "betOfferId": 2289063281,
          "label": "Los Angeles Lakers -6.0",
          "settledInfo": {
            "result": {
              "score": "52-48",
              "correct": [
                "2"
              ],
              "scratched": []
            }
          },
          "status": "LOST",
          "participantId": 1000000226,
          "outcomeTags": []
        }
      ],
      "couponRows": [
        {
          "index": 0,
          "outcomeId": 3003576483,
          "status": "LOST",
          "playedOdds": 1960,
          "payoutOdds": 0,
          "bestOddsGuaranteed": false,
          "tags": [],
          "selectionType": "SIMPLE"
        }
      ],
      "events": [
        {
          "eventId": 1008151189,
          "homeName": "Los Angeles Lakers",
          "awayName": "Oklahoma City Thunder",
          "eventName": "Los Angeles Lakers - Oklahoma City Thunder",
          "eventGroups": [
            {
              "id": 1000093204,
              "name": "Basketball"
            },
            {
              "id": 1000093652,
              "name": "NBA"
            }
          ],
          "eventStartDate": "2021-11-05T02:30:00Z"
        }
      ],
      "betOffers": [
        {
          "betOfferId": 2289063281,
          "boType": "Handicap",
          "boTypeId": 1,
          "criterion": "Handicap - 1st Half",
          "line": -6000,
          "tags": []
        }
      ]
    }
      ],
  "range": {
    "start": 0,
    "size": 420,
    "more": false
  }
}
Необходимо сложить в список все значения payout, у которых предок (хз, правильно ли я выражаюсь) placedDate содержит текст 2021-11-04
Т.е. в список должно попасть 2 значения:
13090
14840
 
Последнее редактирование:

Кто просматривает тему: (Всего: 1, Пользователи: 0, Гости: 1)