尝试根据“订单”值插入/排序列表

Posted

技术标签:

【中文标题】尝试根据“订单”值插入/排序列表【英文标题】:Trying to insert/sort a list based on 'Order' value 【发布时间】:2022-01-01 22:03:41 【问题描述】:

我正在创建一个文档应用程序,允许我企业内部的人员访问有关某些软件的文档。有了这个,我有一个页面,任何管理员都可以管理类别和用户。为此,我希望管理员能够更改应该在我的 NavigationMenu 上显示的类别的顺序。现在,它应该根据 NavigationMenu 中的 Order 正确排序类别的部分起作用了。但是当我尝试编辑现有类别及其订单号时,订单不会相应更新,请参见以下示例:

这是在编辑现有类别之前,这些类别是新添加/制作的

这是在编辑类别之后,“React”应该是 Order 2,API 应该是 Order 0,Test 应该是 Order 1

如您所见,顺序不再有意义。显然,任何订单都不能超过 1 个。

现在,问题很可能来自这段代码。

CategoryService.cs

public async Task<List<Category>> InsertCategory(Category category)
        
            await GetCategories();
            for (int i = 0; i < Categories.Where(c => c.Order >= category.Order).Count(); i++)
            
                Categories[i].Order++;

                if (Categories[i].Order == category.Order)
                
                    Categories[i].Order--;
                    break;
                
            

            await categoryRepository.InsertAsync(Categories);
            EventHelper.NotifyCategoryListChanged(Categories, EventArgs.Empty);
            return Categories;
        

代码顺序如下:

CategoryDialog.razor

private async void SaveCategory(Category category)
    
        if(!string.IsNullOrEmpty(category.Name))
        
            await categoryService.SaveCategory(category);
            Snackbar.Add("Category " + category.Name + " added", Severity.Success);
            MudDialog.Close(DialogResult.Ok(category.Id));       
        
        else
        
            Snackbar.Add("Please enter a category name.", Severity.Warning);
        
    

上面的代码在按钮按下后被调用。这会传递具有特定订单号的类别,该编号是从简单的下拉菜单中传递的。

SaveCategory 函数如下所示:

CategorySerice.cs

public async Task<Category> SaveCategory(Category category)
        
            await InsertCategory(category);

            if (categoryRepository.GetByIdAsync(category.Id) == null)
            
                await categoryRepository.AddAsync(category);
            
            else
            
                await categoryRepository.SaveAsync(category);
            

            EventHelper.NotifyCategoryListChanged(Categories, EventArgs.Empty);

            return category;
        

此函数在实际保存/添加任何内容到数据库之前调用有问题的函数。因此它可以发生在新添加或编辑的类别中。

在此之后,会触发一个事件来通知我的 NavigationMenu 已经进行了更改,并且它应该重新渲染以显示这一点。这没有问题。

但我不知道在更改订单时如何正确列出订单。 快速提醒,编辑现有类别时,此功能不起作用。例如,如果我要在订单 2 中添加一个新类别。它确实可以毫无问题地正确转移所有内容。

欢迎任何帮助!

【问题讨论】:

我不知道它是否相关,但如果GetByIdAsync 是真正的异步,if (categoryRepository.GetByIdAsync(category.Id) == null) 永远不会是真的。因为无论如何它都会返回一个Task 对象。应该是if ( await categoryRepository.GetByIdAsync(category.Id) == null) @Elder 你说得对,我已经改变了。但这似乎不是问题的一部分。不过感谢您的提醒! 【参考方案1】:

所以如果用户尝试用说订单 2 来做第二个,它会减少之前的订单号?

您的循环逻辑不支持这一点,因为您的循环正在增加,所以当它发生时您已经通过了前一个,所以您可能会在之后获得双 1。

我认为,如果您将循环更改为向下运行,就像您下推一样,您会到达您想要的位置,但显然您必须很快支持低于零的订单,但这并不总是得到支持

到:

for (int i = Categories.Count() -1; i >-1; i--)

    if (Categories[i].Order <= category.Order)
    
        Categories[i].Order = Categories[i].Order--;
    

但是为了让所有事情都有意义并且不涉及到这一点,我建议改为提高订单,因为正高数在角落里没有同样的问题可以这么说

或者:

for (int i = 0; i < Categories.Count(); i++)

    if(Categories[i].Order < category.Order) continue;
    Categories[i].Order = Categories[i].Order++;

最终,除非您的实现与我想象的不同,否则您将希望实际添加新类别,而不是再次添加所有类别(不包括新类别)

--FROM: await categoryRepository.InsertAsync(Categories);
--TO:
await categoryRepository.InsertAsync(category);

【讨论】:

我已经尝试了前 2 个解决方案,但这导致在创建新类别时 Order 保持为 0。我不确定最后一个解决方案是做什么的。但如果它有帮助,“类别”是CategoryService.cs 中的一个列表,这是一个单一的事实来源,当GetCategories 被调用时,它会从数据库中获取新信息。 @Rowin 最后假定您要在新类别中插入什么,而不是整个类别列表我没有包含任何关于实际保存更改的内容,对吧?这不是你的问题,你已经掌握了。因此,由于您的比较,我还假设您的类别参数中的顺序已经正确设置,我们看不到它是如何设置的。你在调用 SaveCategory 之前已经设置了吗?因为我们不操纵参数类别,而只是简单地添加它,唯一的可能是它总是 0? Order 中的值来自一个下拉菜单,U 可以选择 0 到当前类别数量,或者创建一个时,0 到当前类别数量 + 1。它正在传递沿着 SaveCategory。我现在要做的是创建一个“新”列表。一切都被转移到为新类别腾出位置。之后它被保存并实际添加到数据库中。这在创建新类别时效果很好,但在编辑现有文档时,它不会相应地向上移动以保持正确的顺序。

以上是关于尝试根据“订单”值插入/排序列表的主要内容,如果未能解决你的问题,请参考以下文章

在 Java 中,如何根据另一个列表对一个列表进行排序?

Django请求GET参数值列表

Sonata Admin - 按计算值排列的订单列表

插入排序链接列表Java

根据值列表对 NSArray 进行排序? [复制]

算法:插入排序列表