声振论坛

 找回密码
 我要加入

QQ登录

只需一步,快速开始

楼主: 花如月

[编程技巧] 游程平滑算法编程实现问题

[复制链接]
 楼主| 发表于 2007-6-11 22:04 | 显示全部楼层
>> a = [1 1 1 1 1 0 0 0 0 0 1 1 1 1 0 0 0 1 1];
T = 4;
b = sprintf('%d',a);
[c,d,e,f]=regexp(b,'0+');
g = cellfun(@length,f);
ind = g<T;
b(c(ind):d(ind)) = '1';
aa = str2num(b')'
??? Function name must be a string.
8兄的程序也报错:@(
回复 支持 反对
分享到:

使用道具 举报

发表于 2007-6-11 22:10 | 显示全部楼层
合并0游程是指将连续的且数量小于门限的1全部替换成0?
 楼主| 发表于 2007-6-11 22:12 | 显示全部楼层

回复 #17 w89986581 的帖子

是的,就是这个意思
发表于 2007-6-11 22:14 | 显示全部楼层
clear all
I=[1 1 1 1 1 0 1 1 1 0 1 0 1 0 0 1 1 1 1 1 1 0 0 0 0 1 1 1 1 1 1];

T = 4;

Idiff = diff(I);
index1 = find(Idiff == 1);
index2 = find(Idiff == -1);
if length(index1) == 0 | length(index2) == 0,
    %%%全1或者全0的情况,根据自己需要单独处理一下
    coutinue;
else
    if length(index1) == length(index2)+1,
        tt = index2 - index1(1:end-1);
        tt = [tt,length(I)-index1(end)];
        index3 = find(tt <= T);
        for ii = 1:length(index3);
            I(index1(index3(ii))+1:index1(index3(ii))+tt(index3(ii))) = 0;
        end
    elseif length(index1) == length(index2)-1,
        if index2(1) <= T;
            I(1:index2(1)) = 0;
        end
        tt = [index2(2:end) - index1];
        index3 = find(tt <= T);
        for ii = 1:length(index3);
            I(index1(index3(ii))+1:index1(index3(ii))+tt(index3(ii))) = 0;
        end
    elseif length(index1) == length(index2),
        if index1(1)>index2(1),
            if index2(1) <= T;
                I(1:index2(1)) = 0;
            end
            tt = index2(2:end) - index1(1:end-1);
            index3 = find(tt <= T);
            for ii = 1:length(index3);
                I(index1(index3(ii))+1:index1(index3(ii))+tt(index3(ii))) = 0;
            end
            if length(I)-index1(end) <=T,
                I(index1(end):end) = 0;
            end
        elseif index1(1) < index2(1),
            tt = index2 - index1;
            index3 = find(tt <= T);
            for ii = 1:length(index3);
                I(index1(index3(ii))+1:index1(index3(ii))+tt(index3(ii))) = 0;
            end
        end
    end
end

I
 楼主| 发表于 2007-6-11 22:14 | 显示全部楼层

回复 #13 eight 的帖子

程序有错:
??? Function name must be a string.
如果需要合并0游程要怎么做呢?你的程序是最简练的
也是最难懂了,但是我一定要弄明白它
发表于 2007-6-11 22:19 | 显示全部楼层
原帖由 花如月 于 2007-6-11 22:14 发表
程序有错:
??? Function name must be a string.
如果需要合并0游程要怎么做呢?你的程序是最简练的
也是最难懂了,但是我一定要弄明白它


我这是个脚本文件(可以砍直接复制到命令窗口运行),不是函数的形式,当然你可以自行修改。在 matlab 中,最简练的程序是最难读懂的。

不过我之前的程序的确有误,应该改为如下(按照你要求修正了,得到的结果是把1改为了0):

  1. a = [1 1 1 1 1 0 0 0 0 0 1 1 1 1 0 0 0 1 1];
  2. T = 4;
  3. b = sprintf('%d',a);
  4. [c,d,e,f]=regexp(b,'1+');
  5. g = cellfun(@length,f);
  6. ind = g<T;
  7. for ii=1:length(ind)
  8.   b(c(ind(ii)):d(ind(ii))) = '0';
  9. end
  10. aa = str2num(b')'
复制代码

[ 本帖最后由 eight 于 2007-6-11 22:23 编辑 ]
 楼主| 发表于 2007-6-11 22:25 | 显示全部楼层

回复 #21 eight 的帖子

我的理解就是脚本文件可以复制到命令行直接运行的。你的程序这样理解:b(c(ind(ii)):d(ind(ii))) = '0';表示合并0游程,如果用b(c(ind(ii)):d(ind(ii))) = '1'是合并1游程 对么?我把你的这2个程序放到命令行后都提示:??? Function name must be a string.是不是最后一句指令有问题?不好意思我太笨了、、help str2num也没看出个什么名堂、、
发表于 2007-6-11 22:28 | 显示全部楼层
老八,这样的函数你是如何找到的,太佩服你拉.神啊~

a = [1 0 0 1 0 0 0 0 1 1 1 1 1 0 0 0 0 0 1 1 1 1 0 0 0 1 1 0 0 0 0 0 0 0];
T = 4;
b = sprintf('%d',a);
[c,d]=regexp(b,'0+');
ind = find(d - c <= T);
for ii = 1:length(ind),
    a(c(ind(ii)):d(ind(ii))) = 1;
end
a

或许这样看好理解一些.
发表于 2007-6-11 22:35 | 显示全部楼层
原帖由 w89986581 于 2007-6-11 22:28 发表
老八,这样的函数你是如何找到的,太佩服你拉.神啊~

a = [1 0 0 1 0 0 0 0 1 1 1 1 1 0 0 0 0 0 1 1 1 1 0 0 0 1 1 0 0 0 0 0 0 0];
T = 4;
b = sprintf('%d',a);
[c,d]=regexp(b,'0+');
ind = find(d - c  


恩,上面的 length 对于逻辑型数据好像无效,这里应该用 find。我刚回来宿舍,没有安装 matlab,不能测试,所以上面的修正依然存在问题,幸亏 w89986581 你帮我检查出来了。明天回去实验室再想想,看能否去掉幅值那个循环。

我是采用正则表达式(regexp 函数)的方法做的,这在我之前写的“[原创]使用文本文件(.txt)进行数据存取的技巧总结”一文中最后那里有提及
 楼主| 发表于 2007-6-11 22:36 | 显示全部楼层

回复 #23 w89986581 的帖子

太佩服2位了,这样改后合并1游程是对的,但是我把a(c(ind(ii)):d(ind(ii))) = 0;后并不能合并0游程。希望你们谁给个最后的总结:loveliness:
发表于 2007-6-11 22:36 | 显示全部楼层
原帖由 花如月 于 2007-6-11 22:25 发表
我的理解就是脚本文件可以复制到命令行直接运行的。你的程序这样理解:b(c(ind(ii)):d(ind(ii))) = '0';表示合并0游程,如果用b(c(ind(ii)):d(ind(ii))) = '1'是合并1游程 对么?我把你的这2个程序放到命令行后 ...


理解有误

直接 copy 到命令窗口中应该没有问题,你的错误我不懂
发表于 2007-6-11 22:38 | 显示全部楼层
原帖由 花如月 于 2007-6-11 22:36 发表
太佩服2位了,这样改后合并1游程是对的,但是我把a(c(ind(ii)):d(ind(ii))) = 0;后并不能合并0游程。希望你们谁给个最后的总结:loveliness:


我21楼的程序就能合并0流程了(关键是 regexp 那句),即把个数少于T的一连串1合并为0,你试试吧,我没有 matlab 也不能测试,抱歉
发表于 2007-6-11 22:49 | 显示全部楼层

回复 #25 花如月 的帖子

%%%  数量小于T的连续1合并
a = [1 0 0 1 0 0 0 0 1 1 1 1 1 0 0 0 0 0 1 1 1 1 0 0 0 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1];
T = 4;
b = sprintf('%d',a);
[c,d]=regexp(b,'1+');   %%%
ind = find(d - c < T);
for ii = 1:length(ind),
    a(c(ind(ii)):d(ind(ii))) = 0;
end
a


%%%  数量小于T的连续0合并
a = [1 0 0 1 0 0 0 0 1 1 1 1 1 0 0 0 0 0 1 1 1 1 0 0 0 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1];
T = 4;
b = sprintf('%d',a);
[c,d]=regexp(b,'0+');   %%%
ind = find(d - c < T);
for ii = 1:length(ind),
    a(c(ind(ii)):d(ind(ii))) = 1;
end
a

评分

1

查看全部评分

 楼主| 发表于 2007-6-12 10:25 | 显示全部楼层

回复 #28 w89986581 的帖子

太谢谢你和8兄的帮忙,问题总算圆满解决了、、
最最后一个问题:在8兄21楼贴的程序里完整的错误信息如下:
??? Function name must be a string.
Error in ==> temp at 5
g = cellfun(@length,f);
程序已经很简练了,8兄有提到有可能去掉那个循环。所以希望看到8兄最后的意见,:loveliness: 连自己都觉得有些贪心了,谁让我懂的这么少呢:@(
发表于 2007-6-12 10:29 | 显示全部楼层
原帖由 花如月 于 2007-6-12 10:25 发表
太谢谢你和8兄的帮忙,问题总算圆满解决了、、
最最后一个问题:在8兄21楼贴的程序里完整的错误信息如下:
??? Function name must be a string.
Error in ==> temp at 5
g = cellfun(@length,f);
程序已经 ...


那个错误可能是由于你的matlab版本不支持匿名函数造成的。你用的是否 matlab 6.5 ?

去掉循环问题我还在考虑,有结果的话自然公布
您需要登录后才可以回帖 登录 | 我要加入

本版积分规则

QQ|小黑屋|Archiver|手机版|联系我们|声振论坛

GMT+8, 2024-5-18 05:06 , Processed in 0.060629 second(s), 16 queries , Gzip On.

Powered by Discuz! X3.4

Copyright © 2001-2021, Tencent Cloud.

快速回复 返回顶部 返回列表