我在Spring Boot中开发了一个应用程序。用户可以上传CSV文件,其中包含数字和代码列。在Java代码中,我能够获得数字列。
CSV.File
number code
12
121
122
123
1211
1212
1231
124
我的目标和回应将给出:
响应-目标
json: [{ number: 12,
child: [{number: 121,
child: [{number: 1211 }, { number: 1212 }]
}]
}, {number: 122 },
{number: 123, child:[{number: 1231}] }.....etc
]
如何按父级和子级在Java中订购此JSON结构?例如。 12是121的父级,而121是1211和1212的父级。
更新:
输入值:
12
121
122
123
1211
1212
1231
14
141
142
1411
25
251
2511
2512
252
253
响应输出
response: [
{
"number": 12,
"child": [
{
"number": 121,
"child": [
{
"number": 1211
},
{
"number": 1212
}
]
},
[
{
"number": 122
}
],
[
{
"number": 123,
"child": [
{
"number": 1231
}
]
}
]
]
},
{
"number": 14,
"child": [
{
"number": 141,
"child": [
{
"number": 1411
}
]
},
[
{
"number": 142
}
]
]
},
{
"number": 25,
"child": [
{
"number": 251,
"child": [
{
"number": 2511
},
{
"number": 2512
}
]
},
[
{
"number": 252
}
],
[
{
"number": 253
}
]
]
}
]
答案 0 :(得分:1)
这不是真正的Java或JSON问题。简而言之,您的问题是-如何在知道列表元素之间的祖先后代关系的情况下,将值列表组装成树结构。
我想出的算法是这样的:
这是一个完整的工作解决方案,可以按您期望的那样生成JSON:
package tmpjavaproj;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;
import com.fasterxml.jackson.annotation.JsonInclude.Include;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
public class Test {
public static class Node implements Comparable<Node> {
public int number;
public List<Node> child; // Although this should actually be called children, not child
public int hashCode() {
return number;
}
public boolean equals(Node node) {
return number == node.number;
}
public int compareTo(Node node) {
return number - node.number;
}
}
public static void main(String[] args) throws Exception {
String[] inputs = { "12", "121", "122", "123", "1211", "1212", "1231", "14", "141", "142", "1411", "25", "251", "2511", "2512", "252", "253" };
Set<Node> roots = new TreeSet<>();
for (String input : inputs) {
Node node = new Node();
node.number = Integer.parseInt(input);
Node root = null;
for (Node rootCandidate : roots) {
if (input.startsWith(String.valueOf(rootCandidate.number))) {
root = rootCandidate;
break;
}
}
if (root == null) {
List<Node> rootsToChildren = new ArrayList<>();
for (Node aRoot : roots) {
if (String.valueOf(aRoot.number).startsWith(String.valueOf(node.number))) {
rootsToChildren.add(aRoot);
}
}
if (!rootsToChildren.isEmpty()) {
node.child = rootsToChildren;
roots.removeAll(rootsToChildren);
}
roots.add(node);
} else {
Node parentCandidate = root;
while (root != null) {
root = null;
if (parentCandidate.child != null) {
for (Node child : parentCandidate.child) {
if (input.startsWith(String.valueOf(child.number))) {
parentCandidate = child;
root = child;
}
}
}
}
if (parentCandidate.child == null) {
parentCandidate.child = new ArrayList<>();
}
parentCandidate.child.add(node);
}
}
Map<String, Set<Node>> response = new HashMap<>();
response.put("response", roots);
ObjectMapper mapper = new ObjectMapper();
mapper.enable(SerializationFeature.INDENT_OUTPUT);
mapper.setSerializationInclusion(Include.NON_NULL);
System.out.println(mapper.writeValueAsString(response));
}
}
答案 1 :(得分:0)
创建一个具有两个字段的响应对象。
.386p
GDT struct
limit_0_15 word ?
base_0_15 word ?
base_16_23 byte ?
access_byt byte ?
fl_limit byte ?
base_24_31 byte ?
GDT ends
main_data segment use16
idt_start:
db 800h dup (?)
idt_info:
dw 2048
dd idt_start
gdt_start:
nul_gdt GDT <0,0,0,0,0,0>
c32_gdt GDT <0,0,0,0,0,0>
d32_gdt GDT <0,0,0,0,0,0>
gdt_info:
dw gdt_info - gdt_start - 1
dd gdt_start
main_data ends
main_code segment use16
assume cs:main_code, ds:main_data, ss:stack16
_start:
mov ax,main_data
mov ds,ax
mov ax,code16
mov es,ax
call es:[Check_A20]
call es:[Set_A20]
call es:[Check_A20]
call es:[Create_GDT]
mov bx,gdt_info
lgdt fword ptr[bx]
mov bx,idt_info
lidt fword ptr[bx]
mov eax,cr0
or eax,1
mov cr0,eax
jmp clear_prefetch_queue
nop
nop
clear_prefetch_queue:
mov eax,0ffffh
mov ebx,0fh
div ebx
exit:
mov ah,4ch
int 21h
main_code ends
code16 segment use16
Wait_8042_command proc ; wait for the kbd controller to get ready to take in commands
in al,64h
test al,2
jnz Wait_8042_command
ret
Wait_8042_command endp
Wait_8042_data proc ; wait for the kbd controller to get ready to take in data
in al,64h
test al,1
jz Wait_8042_data
ret
Wait_8042_data endp
Check_A20 proc
pushf
push ds
push es
push di
push si
cli
xor ax,ax
mov es,ax
mov di,500h
not ax
mov ds,ax
mov si,510h
mov al,byte ptr es:[di]
push ax
mov al,byte ptr ds:[si]
push ax
mov byte ptr es:[di],0
mov byte ptr ds:[si],0ffh
cmp byte ptr es:[di],0ffh
pop ax
mov byte ptr ds:[si],al
pop ax
mov byte ptr es:[di],al
mov ax,0
je check_a20_exit
mov ax,1
check_a20_exit:
pop si
pop di
pop es
pop ds
popf
retf
Check_A20 endp
Set_A20 proc
cli
call Wait_8042_command
mov al,0ADh ;set command to disable kbd
out 64h,al
call Wait_8042_command
mov al,0d0h
out 64h,al ;read from input
call Wait_8042_data
in al,60h ;read input from kbd
push ax
call Wait_8042_command
mov al,0d1h ;write to output
out 64h,al
call Wait_8042_command
pop ax
or al,2
out 60h,al
call Wait_8042_command
mov al,0AEh ;enable kbd controller
out 64h,al
call Wait_8042_command
sti
retf
Set_A20 endp
Create_GDT proc
push ds
mov ax,main_data
mov ds,ax
;NULL Descriptor
;mov cx,4
;rep stosw
;code32 gdt initialized
mov c32_gdt.limit_0_15, 0ffffh
mov c32_gdt.base_0_15, 0h
mov c32_gdt.base_16_23, 0h
mov c32_gdt.access_byt, 9ah
mov c32_gdt.fl_limit, 0cfh
mov c32_gdt.base_24_31, 0h
;data32 gdt initialized
mov d32_gdt.limit_0_15, 0ffffh
mov d32_gdt.base_0_15, 0h
mov d32_gdt.base_16_23, 0h
mov d32_gdt.access_byt, 92h
mov d32_gdt.fl_limit, 0cfh
mov d32_gdt.base_24_31, 0h
pop ds
retf
Create_GDT endp
code16 ends
code32 segment use32
mov eax,0ffffh ;test garbage
mov ebx,0fh
div ebx
code32 ends
data32 segment use32
data32 ends
stack16 segment stack use16
dw 200h dup (?)
stack16 ends
end _start
该课程将为您提供想要的东西。