Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/linq/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用Linq分组的位运算_Linq_Bit Manipulation - Fatal编程技术网

使用Linq分组的位运算

使用Linq分组的位运算,linq,bit-manipulation,Linq,Bit Manipulation,我有一个类似于 public class PermList { public int UserId { get; set; } public int GroupId { get; set; } public int ModuleId { get; set; } public int BitMaskedPermission { get; set; } public List<PermList> TestData() {

我有一个类似于

public class PermList
{
    public int UserId { get; set; }
    public int GroupId { get; set; }
    public int ModuleId { get; set; }
    public int BitMaskedPermission { get; set; }

    public List<PermList> TestData()
    {
        List<PermList> theList = new List<PermList>();
        PermList sample1 = new PermList {BitMaskedPermission = 15, GroupId = 3, ModuleId = 2, UserId = 1};
        theList.Add(sample1);
        PermList sample2 = new PermList { BitMaskedPermission = 2, GroupId = 3, ModuleId = 1, UserId = 1 };
        theList.Add(sample2);
        PermList sample3 = new PermList { BitMaskedPermission = 48, GroupId = 2, ModuleId = 2, UserId = 1 };
        theList.Add(sample3);
        return theList;
    }
}
公共类列表
{
public int UserId{get;set;}
public int GroupId{get;set;}
public int ModuleId{get;set;}
公共整数位掩码权限{get;set;}
公共列表TestData()
{
列表列表=新列表();
PermList sample1=新的PermList{BitMaskedPermission=15,GroupId=3,ModuleId=2,UserId=1};
添加列表(样本1);
PermList sample2=新的PermList{BitMaskedPermission=2,GroupId=3,ModuleId=1,UserId=1};
添加列表(样本2);
PermList sample3=新的PermList{BitMaskedPermission=48,GroupId=2,ModuleId=2,UserId=1};
添加列表(样本3);
返回列表;
}
}

我想使用分组模块ID向位掩码许可证申请或。这是我想要的

如何使用Linq实现这一点


TIA.

可能是这样的:

PermList p=new PermList();
    var result= (
        from test in p.TestData()
        group test by new{test.UserId,test.ModuleId} into g
        select new
        {
            g.Key.UserId,
            g.Key.ModuleId,
            BitMaskedPermission= g.Sum (x =>x.BitMaskedPermission )
        }
    );

也许是这样的:

PermList p=new PermList();
    var result= (
        from test in p.TestData()
        group test by new{test.UserId,test.ModuleId} into g
        select new
        {
            g.Key.UserId,
            g.Key.ModuleId,
            BitMaskedPermission= g.Sum (x =>x.BitMaskedPermission )
        }
    );

如果要执行的聚合操作不是内置操作之一(
Sum
Max
等),则必须转到
Aggregate
,它更详细,但功能也更强大。给你,你想要什么

var data = TestData();
var grouped = 
    from permList in data
    group permList by new { permList.UserId, permList.ModuleId } into g
    select new { // or a named class if you have one
        g.Key.UserId,
        g.Key.ModuleId,
        BitMaskedPermission 
            = g.Aggregate(0, (acc, curr) => acc | curr.BitMaskedPermission)
    };
在这里,我们传递一个函数,该函数接受当前值和当前值,并对它们进行位运算以获得当前累加器值

如果您更喜欢方法链接语法,它将如下所示(由提供):


如果要执行的聚合操作不是内置操作之一(
Sum
Max
等),则必须转到
Aggregate
,它更详细,但功能也更强大。给你,你想要什么

var data = TestData();
var grouped = 
    from permList in data
    group permList by new { permList.UserId, permList.ModuleId } into g
    select new { // or a named class if you have one
        g.Key.UserId,
        g.Key.ModuleId,
        BitMaskedPermission 
            = g.Aggregate(0, (acc, curr) => acc | curr.BitMaskedPermission)
    };
在这里,我们传递一个函数,该函数接受当前值和当前值,并对它们进行位运算以获得当前累加器值

如果您更喜欢方法链接语法,它将如下所示(由提供):


这确实适用于示例数据,但假设
BitMaskedPermission
对于
ModuleId
2
行都是
15
:此代码将给出
30
,这将是错误的。sum不一定能满足您的要求。如果有两个位掩码都是32,那么组合它们的结果应该是32,而不是64。这确实适用于样本数据,但假设
位掩码许可
对于
模块ID
2行都是
15
:此代码将给出
30
,这是错误的。sum不一定会做你想做的事。如果你有两个位掩码都是32,那么组合它们的结果应该是32,而不是64,因为我用另一种形式做了这件事,所以我给出了与之等价的方法:
PermList.TestData().GroupBy(x=>new{x.UserId,x.ModuleId})。选择(x=>new{x.Key.UserId,x.Key.ModuleId,mask=x.Aggregate(0,(acc,curr)=>acc | curr.BitMaskedPermission)})
。如果您愿意,请随时将其编辑到您的答案中(或者修改和编辑或其他我认为您的聚合是错误的内容)。我认为您需要g.Aggregate(0,(acc,curr)=>acc | curr.BitMaskedPermission)(即将累加器默认值设置为0,并使用位掩码,而不是PermList对象。@Chris感谢您的捕获。顺便说一句,如果您愿意使用序列的第一个元素作为初始累加器值(如我们所示),你。事实上,我刚刚检查过,你确实需要初始累加器。如果没有它,则使用序列的第一个元素,但这当然是一个PermList对象,而我们需要一个int。虽然AakashM的答案正确指出了解决方案并对聚合进行了很好的解释,但需要Chris的更新来解决问题。谢谢。还有因为我是以另一种形式做这件事的,所以我给出了与之等价的方法:
PermList.TestData().GroupBy(x=>new{x.UserId,x.ModuleId})。选择(x=>new{x.Key.UserId,x.Key.ModuleId,mask=x.Aggregate(0,(acc,curr)=>acc | curr.BitMaskedPermission)
。如果需要,请随意编辑到您的答案中(或者修改和编辑或者其他我认为你的聚合是错误的。你需要g.Aggregate(0,(acc,curr)=>acc | curr.BitMaskedPermission)我认为(即将累加器默认值设置为0,并使用位掩码,而不是PermList对象。@Chris感谢您的捕获。顺便说一句,如果您愿意使用序列的第一个元素作为初始累加器值(如我们所示),你。事实上,我刚刚检查过,你确实需要初始累加器。如果没有它,则使用序列的第一个元素,但这当然是一个PermList对象,而我们需要一个int。虽然AakashM的答案正确地指出了解决方案并对聚合进行了很好的解释,但需要Chris的更新来解决问题。谢谢。