Android中的Firebase数据描述排序
我正在Firebase存储中存储数据 对象Android中的Firebase数据描述排序,android,firebase,sorting,firebase-realtime-database,Android,Firebase,Sorting,Firebase Realtime Database,我正在Firebase存储中存储数据 对象注释带有属性时间戳。当我将数据从设备推送到Firebase时,我用currentTime填充时间戳,并存储在long数据类型中 当我使用firebaseRef.orderByChild(“timestamp”).limitToLast(15)检索数据时,结果没有按照我的预期排序 我甚至玩弄规则,但没有结果: { "rules": { ".read": true, ".write": true, ".
注释
带有属性时间戳
。当我将数据从设备推送到Firebase时,我用currentTime填充时间戳
,并存储在long
数据类型中
当我使用firebaseRef.orderByChild(“timestamp”).limitToLast(15)检索数据时,
结果没有按照我的预期排序
我甚至玩弄规则,但没有结果:
{
"rules": {
".read": true,
".write": true,
".indexOn": "streetrate",
"streetrate": {
".indexOn": ".value"
}
}
}
我尝试将
时间戳
存储在字符串
数据类型中,问题相同。Firebase可以按给定属性按升序排序项目,然后返回前N个项目(limitToFirst()
)或最后N个项目(limitToLast()
)。没有办法表明您希望项目按降序排列
有两个选项可以获得您想要的行为:
-1 * new Date().getTime();
我通过扩展FirebaseListAdapter并重写getItem方法解决了问题:
public abstract class ReverseFirebaseListAdapter<T> extends FirebaseListAdapter<T> {
public ReverseFirebaseListAdapter(Activity activity, Class<T> modelClass, int modelLayout, Query ref) {
super(activity, modelClass, modelLayout, ref);
}
public ReverseFirebaseListAdapter(Activity activity, Class<T> modelClass, int modelLayout, DatabaseReference ref) {
super(activity, modelClass, modelLayout, ref);
}
@Override
public T getItem(int position) {
return super.getItem(getCount() - (position + 1));
}
公共抽象类ReverseFirebaseListAdapter扩展FirebaseListAdapter{
公共ReverseRefRebeSelistAdapter(活动活动、类modelClass、int modelLayout、查询引用){
超级(活动、模型类、模型布局、参考);
}
public ReverseRefRebeSelistAdapter(活动活动、类modelClass、int modelLayout、数据库参考ref){
超级(活动、模型类、模型布局、参考);
}
@凌驾
公共T getItem(内部位置){
返回super.getItem(getCount()-(位置+1));
}
}基于
@Override
public T getItem(int position) {
return super.getItem(getCount() - (position + 1));
}
对不自动更新FirebaseRecyclerView(实时更改中不会触发PopulateViewHolder)有奇怪的影响。因此,最好的选择是使用负键索引数据在客户端排序很简单,不需要更多的系统资源。 每个数据快照都有previousChildkey字段。如果你想描述排序,想象一下前一个childkey是nextChildKey。 这是我的样本:
class LessonFirebaseArray<ObjectModel>{
private ArrayList<ObjectModel> mItems;
...
public LessonFirebaseArray() {
mItems = new ArrayList<>();
}
public int addItem(ObjectModel item, boolean isReverse){
int index;
if (item.getPreviousChildKey() != null) {
index = getIndexForKey(item.getPreviousChildKey());
if (index < 0) {
index = mItems.size();
}else if(index>0 && !isReverse) {
index = index + 1;
}
}else{
index = mItems.size();
}
mItems.add(index, item);
notifyInsertedListeners(index);
return index;
}
private int getIndexForKey(String key) {
int index = 0;
for (ObjectModel snapshot : mItems) {
if (snapshot.getKey().equals(key)) {
return index;
} else {
index++;
}
}
return -1;
}
private void notifyInsertedListeners(int index) {
if (mListener != null) {
mListener.onInserted(index);
}
}
}
类LessonFirebaseArray{
私有数组列表;
...
公共课FirebaseArray(){
mItems=新的ArrayList();
}
public int addItem(ObjectModel项,布尔值为everse){
整数指数;
if(item.getPreviousChildKey()!=null){
index=getIndexWorkey(item.getPreviousChildKey());
如果(指数<0){
index=mItems.size();
}否则如果(索引>0&!isReverse){
指数=指数+1;
}
}否则{
index=mItems.size();
}
添加(索引,项目);
notifyInsertedListeners(索引);
收益指数;
}
私有int GetIndexWorkey(字符串键){
int指数=0;
用于(对象模型快照:mItems){
if(snapshot.getKey().equals(key)){
收益指数;
}否则{
索引++;
}
}
返回-1;
}
私有void notifyInsertedListeners(int索引){
if(mListener!=null){
mListener.onInserted(索引);
}
}
}
如果您使用recycler视图呈现数据,我会找到一个很好的解决方案
mLayoutManager = new LinearLayoutManager(getActivity());
mLayoutManager.setReverseLayout(true);
mLayoutManager.setStackFromEnd(true);
// And set it to RecyclerView
mRecyclerView.setLayoutManager(mLayoutManager);
它将反转数据渲染
private static class ChatMessageViewHolder extends RecyclerView.ViewHolder {
TextView messageText;
TextView nameText;
public ChatMessageViewHolder(View itemView) {
super(itemView);
nameText = (TextView)itemView.findViewById(android.R.id.text1);
messageText = (TextView) itemView.findViewById(android.R.id.text2);
}
}
FirebaseRecyclerViewAdapter<ChatMessage, ChatMessageViewHolder> adapter;
ref = new Firebase("https://<yourapp>.firebaseio.com");
RecyclerView recycler = (RecyclerView)
findViewById(R.id.messages_recycler);
recycler.setHasFixedSize(true);
//////////////////////////////////////////////////////////
mLayoutManager = new LinearLayoutManager(getActivity());
mLayoutManager.setReverseLayout(true);
mLayoutManager.setStackFromEnd(true);
recycler.setLayoutManager(mLayoutManager);
/////////////////////////////////////////////////////////
adapter = new FirebaseRecyclerViewAdapter<ChatMessage, ChatMessageViewHolder>(ChatMessage.class, android.R.layout.two_line_list_item, ChatMessageViewHolder.class, mRef) {
public void populateViewHolder(ChatMessageViewHolder chatMessageViewHolder, ChatMessage chatMessage) {
chatMessageViewHolder.nameText.setText(chatMessage.getName());
chatMessageViewHolder.messageText.setText(chatMessage.getMessage());
}
};
recycler.setAdapter(mAdapter);
私有静态类ChatMessageViewHolder扩展了RecyclerView.ViewHolder{
文本查看消息文本;
文本视图名称文本;
public ChatMessageViewHolder(查看项目视图){
超级(项目视图);
nameText=(TextView)itemView.findViewById(android.R.id.text1);
messageText=(TextView)itemView.findViewById(android.R.id.text2);
}
}
FirebaseRecycleServiceAdapter适配器;
ref=新火基(“https://.firebaseio.com");
RecyclerView回收器=(RecyclerView)
findViewById(R.id.messages\u recycler);
回收商。setHasFixedSize(真);
//////////////////////////////////////////////////////////
mLayoutManager=新的LinearLayoutManager(getActivity());
mLayoutManager.setReverseLayout(true);
mLayoutManager.setStackFromEnd(true);
回收商。setLayoutManager(mLayoutManager);
/////////////////////////////////////////////////////////
适配器=新的FirebaseRecycleServiceAdapter(ChatMessage.class,android.R.layout.two\u line\u list\u项,ChatMessageViewHolder.class,mRef){
public void populateViewHolder(ChatMessageViewHolder ChatMessageViewHolder,chatmessagechatmessage){
chatMessageViewHolder.nameText.setText(chatMessage.getName());
chatMessageViewHolder.messageText.setText(chatMessage.getMessage());
}
};
回收商。setAdapter(mAdapter);
我看不到任何反转数据的选项。但一个残酷的方法是获取数据
List<ModelClass> mList=new ArrayList();
public void onDataChange(DataSnapshot dataSnapshot)
{
mList.clear();
for(DataSnapshot children: dataSnapshot.getChildren()){
ModelClass modelClass=children.getValue(ModelClass.class);
mList.add(modelClass);
}
Collections.reverse(mList);
Adapter.notifyDataSetChanged();
}
List mList=new ArrayList();
公共void onDataChange(DataSnapshot DataSnapshot)
{
mList.clear();
for(DataSnapshot子项:DataSnapshot.getChildren()){
ModelClass ModelClass=children.getValue(ModelClass.class);
mList.add(模型类);
}
收款。反向(mList);
Adapter.notifyDataSetChanged();
}
Swift 3:
let query = firebase.child(YourQueryPath).queryOrdered(byChild: YourQueryChild).queryLimited(toLast: YourLimit)
query.observeSingleEvent(of: .value, with: { (snapshot) in
// Reverse order here to get top **YourLimit** results in descending order
})
可以使用
android.support.v7.util.SortedList对子项按时间戳排序
class post{
private Object time;
public Object getTime() {
return time;
}
public void setTime(Object time) {
this.time = time;
}
...//rest code}
SortedList<post> data;
data = new SortedList<post>(post.class, new SortedList.Callback<post>() {
@Override
public int compare(post o1, post o2) {
Long o1l = Long.parseLong(o1.getTime().toString());
Long o2l = Long.parseLong(o2.getTime().toString());
return o2l.compareTo(o1l);
}......//rest code
ref.addChildEventListener(new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
mSwipeRefreshLayout.setRefreshing(true);
post p=dataSnapshot.getValue(post.class);
data.add(p);
}...// rest code
class post{
私有对象时间;
公共对象getTime(){
返回时间;
}
公共无效设置时间(对象时间){
这个时间=时间;
}
…//rest代码}
分类列表数据;
data=new SortedList(post.class,new SortedList.Callback(){
@凌驾
公共整数比较(o1后、o2后){
Long o1l=Long.parseLong(o1.getTime().toString());
Long o2l=Long.parseLong(o2.getTime().toString());
将o2l.比较器返回到(o1l);
}..//rest代码
ref.addChildEventListener(新的ChildEventListener(){
@凌驾
一次CHILDADDED(DATASNAPD)的公共空白
var a=[]; //declaring an array a.
var num=snapshot.numChildren(); //storing number of children in var num.
a.push(snapshot.val()); // pushing data in the array.
if (a.length==num){ //checking if length of array is same as number of children.
a.reverse(); //reversing the array elements.
for(i=0; i<num; i++){
a[i].name;//this will sort the data in descending order.
}
}
-3
-2
-1
citiesRef.orderBy("name", "desc").limit(3)
FirebaseFirestore.getInstance().collection("leaderboard")
.orderBy("score")
.addSnapshotListener { snapshot, exception ->
if (exception != null) {
Log.e("Exception:", "Could not retrieve scores ${exception.localizedMessage}")
}
if (snapshot != null) {
scores.clear()
for (document in snapshot.documents) {
val data = document.data
val name = data?.get("name") as? String
val score = data?.get("score") as? Number
val documentId = document.id
val newScore = Score(name, score, documentId)
scores.add(newScore)
}
scores.reverse()
scoresAdapter.notifyDataSetChanged()
}
}
Collections.sort(list, new Comparator<ModuleClass>() {
@Override
public int compare(ModuleClass module, ModuleClass t1) {
return Integer.compare(module.getViews(), t1.getViews());
}
});
FirebaseDatabase.getInstance().getReference().child("parent_id")
.child("id").orderByChild("count");
tpDBListener = tpDatabaseRef.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(@NonNull DataSnapshot snapshot) {
tpUploads.clear();
for(DataSnapshot postSnapshot : snapshot.getChildren()){
newUpload pupload = postSnapshot.getValue(newUpload.class);
pupload.setKey(postSnapshot.getKey());
tpUploads.add(pupload);//add new object on end
//tpUploads.add(0,pupload);//add new object at beginning
}
tpAdapter.notifyDataSetChanged();
}
@Override
public void onCancelled(@NonNull DatabaseError error) {
Toast.makeText(home.this, error.getMessage(),Toast.LENGTH_SHORT).show();
}
});
tpUploads.add(0, pupload);//add new object at beginning
.orderBy("child_ID")
@Override
public void onDataChange(DataSnapshot dataSnapshot)
{
desireList.clear();
List<YourModel>tempList = new ArrayList<>();//Create temp list Object.
for (DataSnapshot dataSnapshotList : dataSnapshot.getChildren())
{
tempList.add(new YourModel(
dataSnapshotList.child("Name").getValue() + "",
dataSnapshotList.getKey() + "",
dataSnapshotList.child("ORDERBY").getValue() + ""));
}
//Save object list in reverse order start.
for (int i =tempList.size(); i>0; i--)
{
desireList.add(tempList.get(i-1));
}
//Save object list in reverse order end.
tempList.clear(); //To clear memory only(not required.)
//Then update your adapter
yoursAdapter.notifyDataSetChanged();
}