将静态数组搜索变成可观察搜索
Posted
技术标签:
【中文标题】将静态数组搜索变成可观察搜索【英文标题】:Turn static array search into an observable search 【发布时间】:2018-09-07 16:34:23 【问题描述】:我有一个问题我想不通..
我的这个函数在我的静态数组上运行良好,但现在我想把它变成我的 obseravble 中的搜索。
这是我在 home.html 中的搜索栏:
<ion-searchbar [(ngModel)]="searchKey" [formControl]="searchControl" (ionInput)="onInput($event)" (ionCancel)="onCancel($event)"></ion-searchbar>
这里是 home.ts:
export class HomePage
searchControl: FormControl;
searching: any = false;
restaurantsList: Observable<any[]>;
constructor()
this.restaurantsList = this.restaurantService.getRestaurantList();
this.searchControl = new FormControl();
ionViewDidLoad()
this.searchControl.valueChanges.debounceTime(700).subscribe(search =>
this.searching = false;
this.setFilteredItems();
);
setFilteredItems()
this.restaurantService.filterRestaurants(this.searchKey).subscribe(
foundRestaurant => this.restaurantsList = foundRestaurant
)
console.log(this.restaurantService.filterRestaurants(this.searchKey));
onInput(event)
this.searching = true;
这是 restaurant-service.ts:
export class RestaurantService
restaurantsRef: AngularFireList<any>;
restaurantsList: Observable<any[]>;
constructor(
public afDb: AngularFireDatabase
)
this.restaurantsRef = afDb.list('/restaurants');
this.restaurantsList = this.restaurantsRef.valueChanges();
getRestaurantList()
return this.restaurantsList;
filterRestaurants(searchKey: string)
let key: string = searchKey.toUpperCase();
return this.restaurantsList.map(
restaurantsList => restaurantsList.filter(
restaurant => [
restaurant.title.toUpperCase(),
restaurant.address.toUpperCase(),
restaurant.city.toUpperCase(),
restaurant.description.toUpperCase()
].join(' ').indexOf(key) > -1)
);
但在setFilteredItems()
方法中,ide 在this.restaurantList
上说:
Type boolean is not assignable to type Observable<any[]>
有谁知道将餐厅列表更改为过滤后的项目的解决方案吗?
仅供参考,我遵循了本教程:LINK
【问题讨论】:
【参考方案1】:看filterRestaurants
的返回,是一个布尔值。您将 restaurantsList
的属性定义为 Observable。您需要将filterRestaurants
的结果转换为 Observable。
import Observable from 'rxjs/Observable';
const filtered: Observable<boolean> = Observable.of(
this.restaurantService.filterRestaurants(this.searchKey)
);
filtered.subscribe(...);
【讨论】:
在我的情况下如何使用它? 你能帮帮我吗?因为当我尝试声明 const 它还说 Observable对我来说似乎有语法错误。这是key
的即兴版本和正确搜索检查
filterRestaurants(searchKey: string)
//below line isn't needed at all.
//this.restaurantsList.subscribe()
let key: string = searchKey.toUpperCase();
//returns Observable
return this.restaurantsList.map(
restaurantsList =>
restaurantsList.filter(
let result = restaurant => [
restaurant.title.toUpperCase(),
restaurant.address.toUpperCase(),
restaurant.city.toUpperCase(),
restaurant.description.toUpperCase()
].join(' ').indexOf(key) > -1
);
return Observable.of(result);
);
【讨论】:
setFilteredItems()
当我试图将结果分配给 this.restaurantList 时,我的 ide 说类型 'any[]' 不能分配给类型 'Observable'
@Sreinieren 你能把同样的屏幕截图发给我吗?
@Sreinieren 我想查看整个代码,你能更新问题吗?
@pankajparker 将其更新为整个搜索代码
当我登录它时它会返回我找到的餐厅但是我如何更新 this.restaurantList【参考方案3】:
this.restaurantService.filterRestaurants
返回一个 Observable
并且您正在订阅它的结果,并且在 subscribe 方法中您尝试将结果分配给另一个 Observable
。
如果您想订阅 observable 的结果并更新餐厅数组,那么您的 restaurantsList
应该是一个数组:
class HomePage
restaurantsList: any[];
所有代码都应该可以正常工作。
_______________________________________________
或者如果你想用一个新的 observable 更新你的 observable 那么你不应该在订阅方法中这样做
setFilteredItems()
this.restaurantsList = this.restaurantService.filterRestaurants(this.searchKey);
然后在 html 中使用异步管道订阅这个 Observable 并呈现它的值列表(这里我也使用 json 管道进行调试)
restaurantsList | async | json
【讨论】:
感谢您的回答,将检查它,但在这里将 this.restaurantsList 声明为行为主题不是更好吗? @Sreinieren 我不这么认为,因为您不希望在任何地方更改餐厅列表,您只对过滤此列表感兴趣。您的 firebase 是这里的真实来源,您应该仅通过 db 更新列表。 如果我尝试这个,它说类型 Observable 不能分配给类型 any[] 属性长度缺少 Observable 类型 @Sreinieren 您是否要复制所有建议?因为我建议了两种方法,这取决于你想要达到的目标。第一个代码块或第二个+第三个 哦,哈哈,我没看到,你建议将它存储在数组还是新的 observable 中?以上是关于将静态数组搜索变成可观察搜索的主要内容,如果未能解决你的问题,请参考以下文章
怎样将discuz的动态页面生成HTML的静态页面,以便搜索引擎更好的收录我的网站呢?请高手多多指导!
从具有每日档案的静态 HTML/CSS 单页网站创建可搜索档案