Características de downcast dentro de Rc para manipulação de AST
Estou tentando manipular ASTs em Rust. Haverá muitas manipulações, e eu quero que minhas árvores sejam imutáveis, para economizar tempo, todas as referências serãoRc
s.
Meus nós da árvore ficarão assim:
enum Condition {
Equals(Rc<Expression>, Rc<Expression>),
LessThan(Rc<Expression>, Rc<Expression>),
...
}
enum Expression {
Plus(Rc<Expression>, Rc<Expression>),
...
}
Eu quero substituir um nó aleatório de um determinado tipo por outro nó do mesmo tipo. Para fazer operações genéricas em árvores, criei uma característica:
trait AstNode {
fn children(&self) -> Vec<Rc<AstNode>>;
}
E todos os nós implementam isso. Isso me permite percorrer a árvore sem ter que desestruturar cada tipo de nó para cada operação, simplesmente chamandochildren()
.
Também quero clonar um nó ao atualizar apenas um de seus filhos e deixar os outros no lugar. Suponha que eu tenha sido capaz de gerar nós do tipo concreto certo (e estou feliz que o programa entre em pânico se estiver errado). Vou adicionar o seguinte método à característica:
trait AstNode {
fn clone_with_children(&self, new_children: Vec<Rc<AstNode>>) -> Self
where Self: Sized;
}
Meu plano é levar as crianças devolvidas porchilden()
, substitua um deles e chameclone_with_children()
para construir um nó da mesma variante enum, mas com um nó substituído.
Meu problema é como escreverclone_with_children()
.
Eu preciso diminuirRc<AstNode>
paraRc<Expression>
(ou o que você tem), mantendo a refcount dentro doRc
o mesmo, mas nenhuma das bibliotecas de downcast que encontrei parece capaz de fazer isso.
O que eu quero é possível ou devo fazê-lo de maneira completamente diferente?