# Tree & Node

Syntax tree navigation and manipulation functionality. Trees represent the complete parsed structure of source code, while Nodes represent individual elements within the tree hierarchy.

## Tree Capabilities

### Tree Creation and Management

Trees are created by parsers and represent immutable syntax structures.

```typescript { .api }
/**
 * Create a shallow copy of the syntax tree (very fast operation)
 * @returns New Tree instance sharing internal structure
 */
copy(): Tree;

/**
 * Delete the syntax tree and free its resources
 */
delete(): void;

/** The language that was used to parse the syntax tree */
language: Language;
```

### Root Node Access

Access the root node of the syntax tree.

```typescript { .api }
/**
 * Get the root node of the syntax tree
 */
get rootNode(): Node;

/**
 * Get the root node with its position shifted forward by the given offset
 * @param offsetBytes - Byte offset to apply
 * @param offsetExtent - Point offset to apply
 * @returns Root node with adjusted position
 */
rootNodeWithOffset(offsetBytes: number, offsetExtent: Point): Node;
```

**Usage Example:**

```typescript
const tree = parser.parse("let x = 1 + 2;");
const root = tree.rootNode;

console.log(root.type); // "program"
console.log(root.toString()); // S-expression representation

// Get root with offset (useful for embedded parsing)
const offsetRoot = tree.rootNodeWithOffset(10, { row: 1, column: 0 });
```

### Tree Editing

Synchronize trees with source code changes for incremental parsing.

```typescript { .api }
/**
 * Edit the syntax tree to keep it in sync with source code changes
 * @param edit - Description of the edit in both byte offsets and row/column coordinates
 */
edit(edit: Edit): void;

/**
 * Compare this tree to a new tree and get ranges where structure changed
 * @param other - New tree representing the same document after edits
 * @returns Array of ranges with syntactic structure changes
 */
getChangedRanges(other: Tree): Range[];
```

**Usage Example:**

```typescript
const tree = parser.parse("let x = 1;");

// Edit the tree to reflect source change: "let x = 1;" → "let x = 42;"
tree.edit({
  startIndex: 8,
  oldEndIndex: 9,
  newEndIndex: 10,
  startPosition: { row: 0, column: 8 },
  oldEndPosition: { row: 0, column: 9 },
  newEndPosition: { row: 0, column: 10 }
});

// Parse the updated source
const newTree = parser.parse("let x = 42;", tree);

// Get changed ranges
const changes = tree.getChangedRanges(newTree);
console.log("Changed ranges:", changes);
```

### Tree Navigation

Create tree cursors and access parsing ranges.

```typescript { .api }
/**
 * Create a new TreeCursor starting from the root of the tree
 * @returns TreeCursor for efficient tree traversal
 */
walk(): TreeCursor;

/**
 * Get the included ranges that were used to parse the syntax tree
 * @returns Array of ranges that were included during parsing
 */
getIncludedRanges(): Range[];
```

## Node Capabilities

### Node Identity and Position

Access node identification and location information.

```typescript { .api }
/** Unique numeric ID for this node within the tree */
id: number;

/** The byte index where this node starts */
startIndex: number;

/** The position where this node starts */
startPosition: Point;

/** The tree that this node belongs to */
tree: Tree;

/**
 * Get the byte index where this node ends
 */
get endIndex(): number;

/**
 * Get the position where this node ends
 */
get endPosition(): Point;
```

### Node Type Information

Access node type and classification details.

```typescript { .api }
/**
 * Get this node's type as a numerical id
 */
get typeId(): number;

/**
 * Get the node's type as a numerical id as it appears in the grammar, ignoring aliases
 */
get grammarId(): number;

/**
 * Get this node's type as a string
 */
get type(): string;

/**
 * Get this node's symbol name as it appears in the grammar, ignoring aliases
 */
get grammarType(): string;
```

**Usage Example:**

```typescript
const root = tree.rootNode;
const firstChild = root.firstChild;

if (firstChild) {
  console.log("Type:", firstChild.type); // e.g., "lexical_declaration"
  console.log("Type ID:", firstChild.typeId); // e.g., 42
  console.log("Grammar type:", firstChild.grammarType);
  console.log("Position:", firstChild.startPosition); // { row: 0, column: 0 }
  console.log("Byte range:", firstChild.startIndex, "-", firstChild.endIndex);
}
```

### Node Classification

Check node properties and error states.

```typescript { .api }
/**
 * Check if this node is named (corresponds to named rules in grammar)
 */
get isNamed(): boolean;

/**
 * Check if this node is extra (like comments, not required by grammar)
 */
get isExtra(): boolean;

/**
 * Check if this node represents a syntax error
 */
get isError(): boolean;

/**
 * Check if this node is missing (inserted by parser for error recovery)
 */
get isMissing(): boolean;

/**
 * Check if this node has been edited
 */
get hasChanges(): boolean;

/**
 * Check if this node contains any syntax errors anywhere within it
 */
get hasError(): boolean;
```

### Node Content and State

Access node text content and parse state information.

```typescript { .api }
/**
 * Get the string content of this node
 */
get text(): string;

/**
 * Get this node's parse state
 */
get parseState(): number;

/**
 * Get the parse state after this node
 */
get nextParseState(): number;
```

### Node Comparison

Compare nodes for equality.

```typescript { .api }
/**
 * Check if this node is equal to another node
 * @param other - Node to compare with
 * @returns True if nodes are equal
 */
equals(other: Node): boolean;
```

### Child Node Access

Access child nodes by index and field.

```typescript { .api }
/**
 * Get the node's child at the given index (0-based)
 * @param index - Child index to retrieve
 * @returns Child node or null if index is out of bounds
 */
child(index: number): Node | null;

/**
 * Get this node's named child at the given index
 * @param index - Named child index to retrieve
 * @returns Named child node or null if index is out of bounds
 */
namedChild(index: number): Node | null;

/**
 * Get this node's child with the given numerical field id
 * @param fieldId - Field ID to look up
 * @returns Child node or null if no child has this field
 */
childForFieldId(fieldId: number): Node | null;

/**
 * Get the first child with the given field name
 * @param fieldName - Field name to look up
 * @returns Child node or null if no child has this field
 */
childForFieldName(fieldName: string): Node | null;
```

**Usage Examples:**

```typescript
const statement = tree.rootNode.firstChild; // e.g., "lexical_declaration"

if (statement) {
  // Access by index
  const firstChild = statement.child(0); // e.g., "let" keyword
  
  // Access by field name
  const declarations = statement.childForFieldName("declarations");
  
  // Get field names
  const fieldName = statement.fieldNameForChild(1);
  console.log("Field name for child 1:", fieldName);
}
```

### Field Name Lookup

Get field names for child nodes.

```typescript { .api }
/**
 * Get the field name of this node's child at the given index
 * @param index - Child index to check
 * @returns Field name or null if child has no field name
 */
fieldNameForChild(index: number): string | null;

/**
 * Get the field name of this node's named child at the given index
 * @param index - Named child index to check
 * @returns Field name or null if child has no field name
 */
fieldNameForNamedChild(index: number): string | null;
```

### Multiple Children Access

Get arrays of children by field.

```typescript { .api }
/**
 * Get an array of this node's children with a given field name
 * @param fieldName - Field name to filter by
 * @returns Array of child nodes with the given field name
 */
childrenForFieldName(fieldName: string): (Node | null)[];

/**
 * Get an array of this node's children with a given field id
 * @param fieldId - Field ID to filter by
 * @returns Array of child nodes with the given field ID
 */
childrenForFieldId(fieldId: number): (Node | null)[];
```

### Child Navigation by Position

Find children by byte offset.

```typescript { .api }
/**
 * Get the node's first child that contains or starts after the given byte offset
 * @param index - Byte offset to search from
 * @returns Child node or null if no such child exists
 */
firstChildForIndex(index: number): Node | null;

/**
 * Get the node's first named child that contains or starts after the given byte offset
 * @param index - Byte offset to search from
 * @returns Named child node or null if no such child exists
 */
firstNamedChildForIndex(index: number): Node | null;
```

### Child Counts and Direct Access

Get child counts and direct child access.

```typescript { .api }
/**
 * Get this node's number of children
 */
get childCount(): number;

/**
 * Get this node's number of named children
 */
get namedChildCount(): number;

/**
 * Get this node's first child
 */
get firstChild(): Node | null;

/**
 * Get this node's first named child
 */
get firstNamedChild(): Node | null;

/**
 * Get this node's last child
 */
get lastChild(): Node | null;

/**
 * Get this node's last named child
 */
get lastNamedChild(): Node | null;

/**
 * Get array of all children
 */
get children(): (Node | null)[];

/**
 * Get array of all named children
 */
get namedChildren(): (Node | null)[];
```

### Sibling Navigation

Navigate between sibling nodes.

```typescript { .api }
/**
 * Get this node's next sibling
 */
get nextSibling(): Node | null;

/**
 * Get this node's previous sibling
 */
get previousSibling(): Node | null;

/**
 * Get this node's next named sibling
 */
get nextNamedSibling(): Node | null;

/**
 * Get this node's previous named sibling
 */
get previousNamedSibling(): Node | null;
```

### Descendant Operations

Work with descendant nodes in the subtree.

```typescript { .api }
/**
 * Get the descendants of this node that are the given type(s)
 * @param types - Node type name or array of type names to search for
 * @param startPosition - Optional start position to limit search
 * @param endPosition - Optional end position to limit search
 * @returns Array of matching descendant nodes
 */
descendantsOfType(types: string | string[], startPosition?: Point, endPosition?: Point): (Node | null)[];

/**
 * Get the node's number of descendants, including one for the node itself
 */
get descendantCount(): number;

/**
 * Get the smallest node within this node that spans the given byte range
 * @param start - Start byte index
 * @param end - End byte index (optional, defaults to start)
 * @returns Smallest node spanning the range or null
 */
descendantForIndex(start: number, end?: number): Node | null;

/**
 * Get the smallest named node within this node that spans the given byte range
 * @param start - Start byte index
 * @param end - End byte index (optional, defaults to start)
 * @returns Smallest named node spanning the range or null
 */
namedDescendantForIndex(start: number, end?: number): Node | null;

/**
 * Get the smallest node within this node that spans the given point range
 * @param start - Start position
 * @param end - End position (optional, defaults to start)
 * @returns Smallest node spanning the range or null
 */
descendantForPosition(start: Point, end?: Point): Node | null;

/**
 * Get the smallest named node within this node that spans the given point range
 * @param start - Start position
 * @param end - End position (optional, defaults to start)
 * @returns Smallest named node spanning the range or null
 */
namedDescendantForPosition(start: Point, end?: Point): Node | null;
```

**Usage Examples:**

```typescript
// Find all identifier nodes
const identifiers = tree.rootNode.descendantsOfType("identifier");
console.log("Found identifiers:", identifiers.length);

// Find node at specific position
const nodeAtCursor = tree.rootNode.descendantForPosition({ row: 0, column: 5 });
console.log("Node at cursor:", nodeAtCursor?.type);

// Find all function declarations
const functions = tree.rootNode.descendantsOfType("function_declaration");
```

### Parent and Ancestor Navigation

Navigate up the tree hierarchy.

```typescript { .api }
/**
 * Get this node's immediate parent
 */
get parent(): Node | null;

/**
 * Get the node that contains the given descendant
 * @param descendant - Descendant node to find container for
 * @returns Node containing the descendant (may be descendant itself)
 */
childWithDescendant(descendant: Node): Node | null;
```

### Tree Cursor Creation

Create efficient tree cursors from nodes.

```typescript { .api }
/**
 * Create a new TreeCursor starting from this node
 * Note: The given node is considered the root of the cursor
 * @returns TreeCursor for efficient traversal
 */
walk(): TreeCursor;
```

### Node Editing

Edit individual nodes to sync with source changes.

```typescript { .api }
/**
 * Edit this node to keep it in-sync with source code changes
 * Only needed when keeping specific Node instances after tree edits
 * @param edit - Description of the edit
 */
edit(edit: Edit): void;
```

### String Representation

Get textual representation of nodes.

```typescript { .api }
/**
 * Get the S-expression representation of this node
 * @returns String representation showing the tree structure
 */
toString(): string;
```

**Usage Example:**

```typescript
const tree = parser.parse("let x = 1 + 2;");
console.log(tree.rootNode.toString());
// Output: (program (lexical_declaration (let) (variable_declarator (identifier) (number))))
```