Store names in TraitData

This commit is contained in:
Aleksey Kladov 2019-11-26 17:12:16 +03:00
parent 4a0792362e
commit 9bc8f1f4f8
3 changed files with 43 additions and 25 deletions

View file

@ -737,14 +737,11 @@ impl Trait {
} }
pub fn items(self, db: &impl DefDatabase) -> Vec<AssocItem> { pub fn items(self, db: &impl DefDatabase) -> Vec<AssocItem> {
db.trait_data(self.id).items.iter().map(|it| (*it).into()).collect() db.trait_data(self.id).items.iter().map(|(_name, it)| (*it).into()).collect()
} }
pub fn associated_type_by_name(self, db: &impl DefDatabase, name: &Name) -> Option<TypeAlias> { pub fn associated_type_by_name(self, db: &impl DefDatabase, name: &Name) -> Option<TypeAlias> {
let trait_data = db.trait_data(self.id); db.trait_data(self.id).associated_type_by_name(name).map(TypeAlias::from)
let res =
trait_data.associated_types().map(TypeAlias::from).find(|t| &t.name(db) == name)?;
Some(res)
} }
pub fn associated_type_by_name_including_super_traits( pub fn associated_type_by_name_including_super_traits(

View file

@ -261,8 +261,8 @@ fn iterate_trait_method_candidates<T>(
// trait, but if we find out it doesn't, we'll skip the rest of the // trait, but if we find out it doesn't, we'll skip the rest of the
// iteration // iteration
let mut known_implemented = false; let mut known_implemented = false;
for &item in data.items.iter() { for (_name, item) in data.items.iter() {
if !is_valid_candidate(db, name, mode, item.into()) { if !is_valid_candidate(db, name, mode, (*item).into()) {
continue; continue;
} }
if !known_implemented { if !known_implemented {
@ -272,7 +272,7 @@ fn iterate_trait_method_candidates<T>(
} }
} }
known_implemented = true; known_implemented = true;
if let Some(result) = callback(&ty.value, item.into()) { if let Some(result) = callback(&ty.value, (*item).into()) {
return Some(result); return Some(result);
} }
} }

View file

@ -87,7 +87,7 @@ impl TypeAliasData {
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
pub struct TraitData { pub struct TraitData {
pub name: Option<Name>, pub name: Option<Name>,
pub items: Vec<AssocItemId>, pub items: Vec<(Name, AssocItemId)>,
pub auto: bool, pub auto: bool,
} }
@ -97,28 +97,42 @@ impl TraitData {
let name = src.value.name().map(|n| n.as_name()); let name = src.value.name().map(|n| n.as_name());
let auto = src.value.is_auto(); let auto = src.value.is_auto();
let ast_id_map = db.ast_id_map(src.file_id); let ast_id_map = db.ast_id_map(src.file_id);
let container = ContainerId::TraitId(tr);
let items = if let Some(item_list) = src.value.item_list() { let items = if let Some(item_list) = src.value.item_list() {
item_list item_list
.impl_items() .impl_items()
.map(|item_node| match item_node { .map(|item_node| match item_node {
ast::ImplItem::FnDef(it) => FunctionLoc { ast::ImplItem::FnDef(it) => {
container: ContainerId::TraitId(tr), let name = it.name().map(|it| it.as_name()).unwrap_or_else(Name::missing);
let def = FunctionLoc {
container,
ast_id: AstId::new(src.file_id, ast_id_map.ast_id(&it)), ast_id: AstId::new(src.file_id, ast_id_map.ast_id(&it)),
} }
.intern(db) .intern(db)
.into(), .into();
ast::ImplItem::ConstDef(it) => ConstLoc { (name, def)
container: ContainerId::TraitId(tr), }
ast::ImplItem::ConstDef(it) => {
let name = it.name().map(|it| it.as_name()).unwrap_or_else(Name::missing);
let def = ConstLoc {
container,
ast_id: AstId::new(src.file_id, ast_id_map.ast_id(&it)), ast_id: AstId::new(src.file_id, ast_id_map.ast_id(&it)),
} }
.intern(db) .intern(db)
.into(), .into();
ast::ImplItem::TypeAliasDef(it) => TypeAliasLoc { (name, def)
container: ContainerId::TraitId(tr), }
ast::ImplItem::TypeAliasDef(it) => {
let name = it.name().map(|it| it.as_name()).unwrap_or_else(Name::missing);
let def = TypeAliasLoc {
container,
ast_id: AstId::new(src.file_id, ast_id_map.ast_id(&it)), ast_id: AstId::new(src.file_id, ast_id_map.ast_id(&it)),
} }
.intern(db) .intern(db)
.into(), .into();
(name, def)
}
}) })
.collect() .collect()
} else { } else {
@ -128,11 +142,18 @@ impl TraitData {
} }
pub fn associated_types(&self) -> impl Iterator<Item = TypeAliasId> + '_ { pub fn associated_types(&self) -> impl Iterator<Item = TypeAliasId> + '_ {
self.items.iter().filter_map(|item| match item { self.items.iter().filter_map(|(_name, item)| match item {
AssocItemId::TypeAliasId(t) => Some(*t), AssocItemId::TypeAliasId(t) => Some(*t),
_ => None, _ => None,
}) })
} }
pub fn associated_type_by_name(&self, name: &Name) -> Option<TypeAliasId> {
self.items.iter().find_map(|(item_name, item)| match item {
AssocItemId::TypeAliasId(t) if item_name == name => Some(*t),
_ => None,
})
}
} }
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]