如何从AllenNLP的hierplane_tree中提取指定实体的关联JSON块
Got it, let's work through this problem together. You're trying to pull full JSON blocks for all nodes linked to a target entity (like "man" in your example) from AllenNLP's dependency tree output, instead of just the node values your current helper function returns. Here's how to make that happen:
1. Quick Recap of Your Goal
Given a target entity (e.g., "man"), extract the complete JSON objects for every node in the dependency tree that's associated with it—including the entity itself, plus linked nodes like "wearing", "blue", and "shirt" from your example sentence.
2. Context: Existing Code & AllenNLP Setup
First, let's anchor this with the code you're likely working with (based on your description):
AllenNLP Dependency Parser Code
from allennlp.predictors.predictor import Predictor import allennlp_models.tagging # Load pre-trained dependency parser predictor = Predictor.from_path("https://storage.googleapis.com/allennlp-public-models/biaffine-dependency-parser-ptb-2020.04.06.tar.gz") # Example sentence sentence = "When I was walking to the park yesterday, I saw a man wearing a blue shirt." # Get hierplane-formatted dependency tree hierplane_tree = predictor.predict(sentence)["hierplane_tree"]
Existing Helper Function (Extracts Only Values)
def get_all_child_values(node): """Current function that returns only child node text values""" values = [node["word"]] for child in node.get("children", []): values.extend(get_all_child_values(child)) return values
3. Solution: New Function to Extract Full JSON Blocks
We'll build a two-step approach: first locate the target entity's node in the tree, then recursively collect it and all its associated child nodes (as full JSON blocks).
Step 1: Locate the Target Entity's Node
First, a helper to find the exact node corresponding to your target entity:
def find_target_node(target_entity, tree_node): """Recursively search the tree for the node matching the target entity""" if tree_node.get("word") == target_entity: return tree_node # Check all children if current node isn't the target for child in tree_node.get("children", []): found_node = find_target_node(target_entity, child) if found_node: return found_node # Return None if target isn't found return None
Step 2: Extract Target + Associated Child JSON Blocks
Now, collect the target node and all its recursive children as full JSON objects:
def extract_associated_json_blocks(target_entity, hierplane_tree): """Main function to pull full JSON blocks for target entity and its linked nodes""" # Find the target node first target_node = find_target_node(target_entity, hierplane_tree) if not target_node: return [] # Return empty list if target isn't in the tree # Recursively collect the target node and all its children def collect_node_and_children(node): blocks = [node] for child in node.get("children", []): blocks.extend(collect_node_and_children(child)) return blocks return collect_node_and_children(target_node)
4. Test It Out
Run this with your example to see the results:
# Extract blocks for "man" associated_blocks = extract_associated_json_blocks("man", hierplane_tree) # Print each full JSON block for idx, block in enumerate(associated_blocks): print(f"\n--- Associated Node {idx+1} ---") print(f"Word: {block['word']}") print(f"Dependency Relation: {block['attributes'][0]}") print("Full JSON Block:") print(block)
This will output the complete JSON objects for "man", "wearing", "shirt", and "blue"—exactly what you're looking for.
5. Customization (Optional)
If you only want nodes with specific dependency relations (e.g., adjectival modifiers amod, oblique arguments obl), modify the collection function to filter by dependency tags:
def collect_filtered_nodes(node, allowed_deps=None): blocks = [] # Include current node if it matches allowed dependencies (or no filter) if allowed_deps is None or node["attributes"][0] in allowed_deps: blocks.append(node) # Recurse on children for child in node.get("children", []): blocks.extend(collect_filtered_nodes(child, allowed_deps)) return blocks # Usage: Only collect adjectival modifiers and oblique arguments target_node = find_target_node("man", hierplane_tree) filtered_blocks = collect_filtered_nodes(target_node, allowed_deps=["amod", "obl"])
内容的提问来源于stack exchange,提问作者scarpacci

