2015-05-21 12 views
5

Środowisko: JQ 1.5, Windows 64-bit.Przetwarzanie JSON tablic w tablicy z jq

Mam następujący JSON:

{ 
    "unique": 1924, 
    "coordinates": [ 
    { 
     "time": "2015-01-25T00:00:01.683", 
     "xyz": [ 
     { 
      "z": 4, 
      "y": 2, 
      "x": 1, 
      "id": 99 
     }, 
     { 
      "z": 9, 
      "y": 9, 
      "x": 8, 
      "id": 100 
     }, 
     { 
      "z": 9, 
      "y": 6, 
      "x": 10, 
      "id": 101 
     } 
     ] 
    }, 
    { 
     "time": "2015-01-25T00:00:02.790", 
     "xyz": [ 
     { 
      "z": 0, 
      "y": 3, 
      "x": 7, 
      "id": 99 
     }, 
     { 
      "z": 4, 
      "y": 6, 
      "x": 2, 
      "id": 100 
     }, 
     { 
      "z": 2, 
      "y": 9, 
      "x": 51, 
      "id": 101 
     } 
     ] 
    } 
    ] 
} 

i chciałby przekształcić go w formacie CSV z JQ:

unique,time,id,x,y,z 
1924,"2015-01-25T00:00:01.683",99,1,2,4 
1924,"2015-01-25T00:00:01.683",100,8,9,9 

(i tak dalej)

próbowałem kilka rzeczy, takie jak:

jq -r '{unique: .unique, coordinates: .coordinates[].xyz[] | [.id, .x, .y, .z], time: .coordinates.[].time} | flatten | @csv' 

, który dał mi pożądany JSON, ale pomnożony dla każdego id, x, yiz (np. każda unikalna linia pojawia się cztery razy - po jednym dla id, x, y, z).

Przypisywanie numeru do tablicy, takich jak

jq -r '{unique: .unique, coordinates: .coordinates[0].xyz[] | [.id, .x, .y, .z], time: .coordinates.[0].time} | flatten | @csv' 

daje mi pierwszy indeks tablicy coordinates, ale chciałbym je wszystkie, naturalnie.

+0

Dla jakiego języka? JavaScript? –

+2

Z jq (http://stedolan.github.io/jq/) – innocentunremarkable

+0

Mmm. Wymagający bardzo niedawnej kompilacji; Nadal jestem na 1.4. Ale tak jest w przypadku błyszczących funkcji ... –

Odpowiedz

5

Pierwszym krokiem byłoby spłaszczyć wyniki do wierszy.

[{ unique } + (.coordinates[] | { time } + .xyz[])] 

przyniesie to szereg obiektów w rzędzie:

[ 
    { 
    "unique": 1924, 
    "time": "2015-01-25T00:00:01.683", 
    "id": 99, 
    "x": 1, 
    "y": 2, 
    "z": 4 
    }, 
    { 
    "unique": 1924, 
    "time": "2015-01-25T00:00:01.683", 
    "id": 100, 
    "x": 8, 
    "y": 9, 
    "z": 9 
    }, 
    { 
    "unique": 1924, 
    "time": "2015-01-25T00:00:01.683", 
    "id": 101, 
    "x": 10, 
    "y": 6, 
    "z": 9 
    }, 
    { 
    "unique": 1924, 
    "time": "2015-01-25T00:00:02.790", 
    "id": 99, 
    "x": 7, 
    "y": 3, 
    "z": 0 
    }, 
    ... 
] 

Następnie jest jedynie kwestią przetwarzania na rzędach CSV.

["unique","time","id","x","y","z"] as $fields | $fields, (.[] | [.[$fields[]]]) | @csv 
+0

p.s., to powinno działać również dla jq 1.4. –

+0

Dzięki! Używałem paradygmatu flatten/@csv dla poprzednich poleceń - czy twoja metoda konwersji na CSV jest szybsza/bardziej wydajna? – innocentunremarkable

+0

Nie sądzę, żeby "spłaszczać" naprawdę tu działało. Ma na celu spłaszczenie tablic tablic, a nie obiektów. I nie chciałbyś go użyć, ponieważ spłaszczanie obiektu przyniesie wartości. Stracisz powiązane klucze i nie można zagwarantować zamówienia. Konieczne byłoby przekonwertowanie na inne formy pośrednie, aby lepiej to wykorzystać. Podejście, które tu podjąłem, jest bardziej bezpośrednie, więc spodziewam się, że będzie ono relatywnie szybsze niż próba zmuszenia go do pracy z spłaszczaniem. –

Powiązane problemy