【问题标题】:Delete Repeated Consecutive Cells which ONLY include specific value (MATLAB)删除仅包含特定值的重复连续单元格(MATLAB)
【发布时间】:2016-03-23 02:20:46
【问题描述】:

我有一件非常具体的事情需要 Matlab 来完成,但我不确定如何去做。

这是我正在使用的示例:

'B4,9(55)'
'B4,9(55)'
'B2,16,25(99)'
'B2,16,25(99)'
'B17,21,28,29(46)'
'B4,10(56)'
'B4,10(56)'
'B2,15,25(99)'
'B17,20,27,29(45)'

我需要一个脚本来删除连续的重复条目,但如果它包含某个字符串(即 52、55 和 56)。不应删除带有 (99) 的重复条目。所以,我最终想要的是这样的:

'B4,9(55)'
'B2,16,25(99)'
'B2,16,25(99)'
'B17,21,28,29(46)'
'B4,10(56)'
'B2,15,25(99)'
'B17,20,27,29(45)'

这可能吗?


编辑:一些更大的背景...... 我在 EEG 实验室工作,我们使用 Matlab 分析我们的数据。打开 Matlab 后,我运行“eeglab”。然后我打开一个设置文件。我运行一个脚本来创建 EEG 事件列表,并删除某些我不想要的事件类型。

%create a list of events
justevents = {EEG.event.type};

%delete the 201-203s
justevents(strcmp(justevents,'201'))=[];
justevents(strcmp(justevents,'202'))=[];
justevents(strcmp(justevents,'203'))=[];

%delete the 101-130s
justevents(strcmp(justevents,'101'))=[];
justevents(strcmp(justevents,'102'))=[];
justevents(strcmp(justevents,'103'))=[];
justevents(strcmp(justevents,'104'))=[];
justevents(strcmp(justevents,'105'))=[];

(一直到 130)

然后我运行 Suever 给我的代码,但它删除了 52、55 和 56 事件...

这是一个更大的示例数据块,包括我在上面包含的代码中删除的内容。我不确定如何正确格式化它,但这是 Matlab 输出...

mycell = { ...

'B1,12,25(99)'    '201'    '101'    'B18,23,27,29(45)'    'B3,6(55)' ...
'B3,6(55)'    'B2,16,25(99)'    '201'    '102'    'B17,21,28,29(46)' ...
'B4,10(56)'    'B4,10(56)'    'B1,13,25(99)'    '201'    '201'    '103' ...
'B18,24,28,29(46)'    'B3,7(56)'    'B3,7(56)'    'B2,14,25(99)'    '201' ...
'104'    'B17,19,26,29(42)'    'B4,8(52)'    'B4,8(52)'    'B1,13,25(99)' ...
'201'    '105'    'B18,24,28,29(46)'    'B3,7(56)'}

【问题讨论】:

    标签: matlab


    【解决方案1】:

    解决这个问题的一种方法是首先找到所有重复的字符串,并为每个唯一的字符串分配一个索引。您可以使用ismember 的第二个输出轻松完成此操作。

    [~, unique_ind] = ismember(mycell, mycell);
    

    然后,我们可以通过查找具有相同索引值的序列的位置来识别 连续 个重复项。我们可以通过查看差异是否为零来检查这一点。

    consec_dupes = [false, diff(unique_ind) == 0];
    

    然后,我们可以查看每个具有重复值的情况,并使用正则表达式查看它们是否符合条件。如果在字符串中找到 53、55 或 56,则以下将为 true,否则为 false

    ismatch = ~cellfun(@isempty, regexp(mycell(consec_dupes), '\(52|55|56\)'));
    

    现在我们要忽略所有与指定数字不匹配的连续重复项。为此,我们现在可以将所有 匹配的 consec_dupes 值设置为 false

    consec_dupes(consec_dupes) = ismatch;
    

    现在我们只需从原始元胞数组中删除这些匹配的连续重复项。

    mycell(consec_dupes) = [];
    

    总结

    因此将所有这些整合到一个代码块中:

    [~, unique_ind] = ismember(mycell, mycell);
    consec_dupes = [false, diff(unique_ind) == 0];
    ismatch = ~cellfun(@isempty, regexp(mycell(consec_dupes), '\(52|55|56\)'));
    consec_dupes(consec_dupes) = ismatch;
    mycell(consec_dupes) = [];
    

    将此应用于您的示例数据,我们会得到以下结果:

    'B1,12,25(99)'
    '201'
    '101'
    'B18,23,27,29(45)'
    'B3,6(55)'
    'B2,16,25(99)'
    '201'
    '102'
    'B17,21,28,29(46)'
    'B4,10(56)'
    'B1,13,25(99)'
    '201'
    '201'
    '103'
    'B18,24,28,29(46)'
    'B3,7(56)'
    'B2,14,25(99)'
    '201'
    '104'
    'B17,19,26,29(42)'
    'B4,8(52)'
    'B1,13,25(99)'
    '201'
    '105'
    'B18,24,28,29(46)'
    'B3,7(56)'
    

    【讨论】:

    • 我认为这个解决方案非常接近工作,感谢您的帮助!当我测试我在这里包含的示例数据集时,它工作得很好。但是,当我在数据上下文中对其进行测试时,代码会删除其中包含 52、55 和 56 的所有单元格。知道为什么吗?我包含的示例数据集直接取自我实验室生成的数据文件,所以我不太明白为什么它会删除所有 52,55 和 56 案例而不是重复案例
    • @ChristieSmith 嗯,我无法重现。您能否在原始问题中发布一些会触发此问题的示例数据?
    • @ChristieSmith 还要确保您已复制 所有 行。省略toremove(inds(aind)) = false 行肯定会导致您提到的问题
    • toremove(inds(aind)) = false 肯定在其中很快就会有一大块数据,一旦我正确地为stackoverflow格式化它......
    • 另外,justevents 给出了一个 1x514 的矩阵。在测试您的代码时,我使用data = transpose(justevents) 使其与示例数据集的格式相匹配,但它仍然删除了 52、55、56 个事件。
    【解决方案2】:

    首先你必须把你的字符串放在一个单元格中。

    cell = {'B4,9(55)',
    'B4,9(55)',
    'B2,16,25(99)',
    'B2,16,25(99)',
    'B17,21,28,29(46)',
    'B4,10(56)',
    'B4,10(56)',
    'B2,15,25(99)',
    'B17,20,27,29(45)'};
    

    然后,这只是一个选项,您可以通过组合两个索引来选择您的数据。

    [~,index1] = unique(cell); %find the uniques strings.
    index2 = find(cellfun(@isempty,strfind(cell,'99'))==0); %find the string that contains '99'
    index = unique([index1;index2]);
    
    mycell = cell(sort(index))
    

    【讨论】:

    • 我相信 OP 想要指定要删除的项目不一定要排除的项目。
    猜你喜欢
    • 2014-03-31
    • 1970-01-01
    • 1970-01-01
    • 2021-06-20
    • 2016-01-05
    • 2021-03-19
    • 2019-03-04
    • 2022-12-10
    • 1970-01-01
    相关资源
    最近更新 更多