【图像分割】光流生成标签(matlab)

文章目录

  • 1. 框架
  • 2. opticalFlow_label
  • 3. 光流

1. 框架

在这里插入图片描述

2. opticalFlow_label

close all; clear; clc;
% 使用光流进行标签的生成
%% 视频帧的读取
npy_data = readNPY('train.npy');

%% 提取标签的坐标
first_label = squeeze(npy_data(2,1,:,:));
h = fspecial("gaussian", [3, 3], 1);
first_label_g = imfilter(first_label, h, 'replicate');   % 'conv'
first_label_c = edge(first_label_g, "canny");
% imshow(uint8(first_label_c*255));
first_label_double = im2double(first_label_c);
first_label_bw = im2bw(first_label_double, 0.5);
% imshow(uint8(first_label_bw * 255));
[h, w] = size(first_label);
xPos = [];
yPos = [];
step = 0;
for i = 1:h
    for j = 1:w
        if first_label_bw(i, j) == 1
%             xPos = [xPos, i];       % 保存为行
%             yPos = [yPos, j];
              step = step + 1;
              if mod(step, 1) == 0
                  xPos = [xPos; j];   % 保存为列
                  yPos = [yPos; i];
              end
        end
    end
end

%% 逐帧处理
first_frame = squeeze(npy_data(1,1,:,:));
first_frame = uint8(first_frame);
% imshow(first_frame);
[c,frame_num,img_h,img_w] = size(npy_data);
num = 0;
save_npy(1,1,:,:) = first_frame;
save_npy(2,1,:,:) = first_frame;   % 预留一个通道,用于保存标签

for i = 2  % 2:frame_num
    num = num + 1;
    currFrame = squeeze(npy_data(1,i,:,:));
    currFrame = uint8(currFrame);
    pyramidLayer = 4;
    kernelSize = 3;
    sigma = 1.5;
    iterNumMax = 5;
    ww = 13;
    [u, v] = affineLKopticalFlow(first_frame, currFrame, xPos, yPos, pyramidLayer, kernelSize, sigma, iterNumMax, ww);
    
    % 显示
    newFrame = repmat(currFrame, [1, 1, 3]);
    new_xPos = xPos + u;
    new_yPos = yPos + v;
    newFrame1 = zeros(size(currFrame));
    for kk = 1:length(xPos)
        %显示
        newFrame(int16(new_yPos(kk)), int16(new_xPos(kk)), 1) = 255;
        newFrame(:, :, 2) = currFrame;
        newFrame(int16(new_yPos(kk)), int16(new_xPos(kk)), 3) = 0;
        newFrame1(int16(new_yPos(kk)), int16(new_xPos(kk))) = 1;
    end   
    
    save_npy(1,i,:,:) = currFrame;
    save_npy(2,i,:,:) = first_frame;
%     writeNPY(save_npy, "test.npy");
    
    figure(1)
    imshow(newFrame)
    title("Pre")
    % 形态学处理 离散点的连接
    se = strel('disk',51);   % 加大半径 可以进行填充
    fc = imclose(newFrame1, se);
%     imwrite(fc, "fc.jpg")
    % bw = im2bw(fc);
    % fill_img = imfill(bw, "holes");   % 封闭区域
    figure(2)
    imshow(fc)
    title("fc")
    
    %将mask显示在图片上
    mask_frame = repmat(currFrame, [1, 1, 3]);
    [mask_h, mask_w, channel] = size(mask_frame);
    for i = 1:mask_h
        for j = 1:mask_w
            if fc(i, j) == 1
               mask_frame(i, j, 1) = 255;
               mask_frame(:, :, 2) = currFrame;
               mask_frame(i, j, 3) = 0;
            end 
        end
    end
    figure(4)
    imshow(mask_frame)
    title("mask")
    
    first_frame = currFrame;
    xPos = double(int16(new_xPos));
    yPos = double(int16(new_yPos));
    
end

3. 光流

% author        : huangcan
% date           : 2019.4.22
% comment   : this code is an implementation of Local antomical affine optical flow algorithm
% reference   : paper: "Fast Left Ventricle Tracking in 3D Echocardiographic Data Using Anatomical Affine Optical Flow"
% parameter  : 
%                       lastFrame           上一帧的图像
%                       currFrame   当前帧的图像
%                       xPos      要跟踪的点的横坐标
%                       yPos                    要跟踪的点的纵坐标
%                       pyramidLayer    尺度金字塔的层数(包含原始层)
%                       kernelSize         高斯模糊的模板尺寸大小,3即可
%                       sigma               高斯模糊标准差
%                       iterNumMax  迭代次数上限,一般4次即可
%                       ww                      ROI框的尺寸,注意确保多尺度后的尺寸仍在图像范围内

function [u, v] = affineLKopticalFlow(lastFrame, currFrame, xPos, yPos, pyramidLayer, kernelSize, sigma, iterNumMax, ww)

u = zeros(length(xPos),1);
v = zeros(length(xPos),1);

%% build image pyramid
fr1Pyramid = cell(pyramidLayer,1);
fr2Pyramid = cell(pyramidLayer,1);
fr1Pyramid{1} = lastFrame;
fr2Pyramid{1} = currFrame;

h = fspecial('gaussian',[kernelSize kernelSize], sigma);
for i = 2:pyramidLayer
    %h = fspecial('gaussian', [3 3], 0.83^(i-2)); 
    temp1 = imfilter(fr1Pyramid{i-1}, h, 'same');
    temp2 = imfilter(fr2Pyramid{i-1}, h, 'same');
    fr1Pyramid{i} = imresize(temp1, 1/2);
    fr2Pyramid{i} = imresize(temp2, 1/2);
end

%% coarse to fine

g = zeros(length(xPos), 6, pyramidLayer + 1);

for i = pyramidLayer:-1:1
    im1 = im2double(fr1Pyramid{i});
    im2 = im2double(fr2Pyramid{i});
    % for each point, calculate I_x, I_y
    Ix_m = filter2([-1 0 1; -1 0 1; -1 0 1],im1, 'same'); % partial on x
    Iy_m = filter2([-1 -1 -1; 0 0 0; 1 1 1],im1,  'same'); % partial on y

    xPosPyramid = xPos ./ 2^(i-1);
    yPosPyramid = yPos ./ 2^(i-1);

    for xx = 1:length(xPos)
        %x0 = [u; v; ux; uy; vx; vy];这个不是运动矩阵,而是参数矩阵
        %matG = [1+g(xx, 3, i+1) g(xx, 4, i+1) g(xx, 1, i+1); g(xx, 5, i+1) 1+g(xx, 6, i+1) g(xx, 2, i+1); 0 0 1];
        %粗精度下的运动矩阵matG
        matG = [1 0 g(xx, 1, i+1); 0 1 g(xx, 2, i+1); 0 0 1];
        matX0 = [1 0 0;0 1 0;0 0 1] * matG;
        x0 = [matX0(1,3);matX0(2,3);matX0(1,1) - 1;matX0(1,2);matX0(2,1);matX0(2,2) - 1];
        for k = 1:iterNumMax
            % x0为组合仿射矩阵,迭代计算,相对于fr1
            x = calcAAOF(Ix_m, Iy_m, im1, im2, xPosPyramid, yPosPyramid, ww, xx, x0);
            % affine motion combination
            matX1 = [1+x(3) x(4) x(1); x(5) 1+x(6) x(2); 0 0 1];
            matX0 = matX1 * matX0;
            x0 = [matX0(1,3); matX0(2,3); matX0(1,1) - 1; matX0(1,2); matX0(2,1); matX0(2,2) - 1];
        end
        %此时X0为该层金字塔相对于第一帧的仿射参数,matX0为相对于第一帧的仿射矩阵
        if (i >= 2)
            % 为更细精度的分析进行运动放大
            iterFinal = [2 0 0;0 2 0;0 0 1] * matX0;
            g(xx,:,i) = [iterFinal(1,3); iterFinal(2,3); iterFinal(1,1)-1; iterFinal(1,2); iterFinal(2,1); iterFinal(2,2)-1];
        else
            % 最终层不需要变化
            iterFinal = matX0;
            g(xx,:,i) = [iterFinal(1,3); iterFinal(2,3); iterFinal(1,1) - 1; iterFinal(1,2); iterFinal(2,1); iterFinal(2,2) - 1];
        end
    end

        
end

for xx = 1:length(xPos)
    u(xx) = g(xx, 1, 1);
    v(xx) = g(xx, 2, 1);
end

end


% sum
function x = calcAAOF(Ix_m, Iy_m, im1, im2, xPos, yPos, ww, ix, x0)
    %x0 = [u v ux1 ux2 vx1 vx2];

w = floor(ww/2);


if (length(xPos) > 100)
    weightMatPhase = ones(ww,ww);
else
    weightMatPhase = zeros(ww, ww);
    for i = 1 : ww
        for j = 1 : ww
            xc = int16(xPos(ix)) - (ww + 1) / 2 + i;
            yc = int16(yPos(ix)) - (ww + 1) / 2 + j;
            weightMatPhase(j,i) = 0;
            for ii = 1:length(xPos)
                dis = sqrt((double(xc) - double(xPos(ii)))^2 + (double(yc) - double(yPos(ii)))^2);
                if (dis < sqrt(2)*ww)
                    weightMatPhase(j, i) = weightMatPhase(j, i) +1;
                end
            end
        end
    end
end
weight = weightMatPhase(:);


xx = ix;
i = int16(xPos(xx));
j = int16(yPos(xx));
    
%Ix = Ix_m(j-w:j+w, i-w:i+w);
Ix = iGetN(Ix_m,i,j,2*w+1);
%Iy = Iy_m(j-w:j+w, i-w:i+w);
Iy = iGetN(Iy_m, i, j, 2*w+1);

% affine model
newX = zeros(size(Ix));
newY = zeros(size(Iy));
for iSecond = -w:w %x
    for jSecond = -w:w %y
        iiMoveSecond = x0(1) + x0(3)*double(iSecond) + x0(4)*double(iSecond);
        jjMoveSecond = x0(2) + x0(5)*double(jSecond) + x0(6)*double(jSecond);
        newX(jSecond+w+1,iSecond+w+1) = double(i) + iSecond + iiMoveSecond;
        newY(jSecond+w+1,iSecond+w+1) = double(j) + jSecond + jjMoveSecond;
    end
end
% bilinear interp2
newXX = linspace(1, size(im2,2), size(im2,2));
newYY = linspace(1, size(im2,1), size(im2,1));

Xfirst = repmat(newXX, [size(im2,1) 1]);
Yfirst = repmat(newYY', [1 size(im2,2)]);
newIm2 = interp2(Xfirst, Yfirst, im2, newX,newY);
% calculate time difference
%It = newIm2 - im1(j-w:j+w, i-w:i+w);
It = newIm2 - iGetN(im1, i, j, 2*w+1);

Ix = Ix(:);
Iy = Iy(:);
It = It(:);

tempX = linspace(-w, w, 2*w+1);
tempY = linspace(-w, w, 2*w + 1);

xCoord = repmat(tempX, [2*w + 1 1]);
yCoord = repmat(tempY', [1 2*w+ 1]);
xCoord = xCoord(:);
yCoord = yCoord(:);
    

A11 = sum(sum(weight .* Ix .* Ix));% w Ix Ix
A12 = sum(sum(weight .* Ix .* Iy));% w Ix Iy
A13 = sum(sum(xCoord .* weight .* Ix .* Ix));% x w Ix Ix
A14 = sum(sum(yCoord .* weight .* Ix .* Ix));% y w Ix Ix
A15 = sum(sum(xCoord .* weight .* Ix .* Iy));% x w Ix Iy
A16 = sum(sum(yCoord .* weight .* Ix .* Iy));% y w Ix Iy
A21 = sum(sum(weight .* Ix .* Iy));% w Ix Iy
A22 = sum(sum(weight .* Iy .* Iy));% w Iy Iy
A23 = sum(sum(xCoord .* weight .* Ix .* Iy));%x w Ix Iy
A24 = sum(sum(yCoord .* weight .* Ix .* Iy));%y w Ix Iy
A25 = sum(sum(xCoord .* weight .* Iy .* Iy));%x w Iy Iy
A26 = sum(sum(yCoord .* weight .* Iy .* Iy));%y w Iy Iy
A31 = sum(sum(xCoord .* weight .* Ix .* Ix));%x w Ix Ix
A32 = sum(sum(xCoord .* weight .* Ix .* Iy));% x w Ix Iy
A33 = sum(sum(xCoord.^2 .* weight .* Ix .* Ix));%x^2 w Ix Ix
A34 = sum(sum(xCoord .* yCoord .* weight .* Ix .* Ix));% x y Ix Ix
A35 = sum(sum(xCoord .^ 2 .* weight .* Ix .* Iy));% x^2 w Ix Iy
A36 = sum(sum(xCoord .* yCoord .* weight .* Ix .* Iy));% x y w Ix Iy
A41 = sum(sum(yCoord .* weight .* Ix .* Ix));% y w Ix Ix
A42 = sum(sum(yCoord .* weight .* Ix .* Iy));% y w Ix Iy
A43 = sum(sum(xCoord .* yCoord .* weight .* Ix .* Ix));% x y w Ix Ix
A44 = sum(sum(yCoord .^ 2 .* weight .* Ix .* Ix));%y^2 w Ix Ix
A45 = sum(sum(xCoord .* yCoord .* weight .* Ix .* Iy));% x y w Ix Iy
A46 = sum(sum(yCoord .^ 2 .* weight .* Ix .* Iy));% y^2 w Ix Iy
A51 = sum(sum(xCoord .* weight .* Ix .* Iy));% x^2 w Ix Iy
A52 = sum(sum(xCoord .* weight .* Iy .* Iy));% x w Iy Iy
A53 = sum(sum(xCoord .^ 2 .* weight .* Ix .* Iy));% x^2 w Ix Iy
A54 = sum(sum(xCoord .* yCoord .* weight .* Ix .* Iy));% x y w Ix Iy
A55 = sum(sum(xCoord .^ 2 .* weight .* Iy .* Iy));% x^2 w Iy Iy
A56 = sum(sum(xCoord .* yCoord .* weight .* Iy .* Iy));% x y w Iy Iy
A61 = sum(sum(yCoord .* weight .* Ix .* Iy));% y w Ix Iy
A62 = sum(sum(yCoord .* weight .* Iy .* Iy));%y w Iy Iy
A63 = sum(sum(xCoord .* yCoord .* weight .* Ix .* Iy));% x y w Ix Iy
A64 = sum(sum(yCoord .^ 2 .* weight .* Ix .* Iy));% y^2 w Ix Iy
A65 = sum(sum(xCoord .* yCoord .* weight .* Iy .* Iy));% x y w Iy Iy
A66 = sum(sum(yCoord .^ 2 .* weight .* Iy .* Iy));% y^2 w Iy Iy

A = [A11 A12 A13 A14 A15 A16; A21 A22 A23 A24 A25 A26; A31 A32 A33 A34 A35 A36; A41 A42 A43 A44 A45 A46; A51 A52 A53 A54 A55 A56; A61 A62 A63 A64 A65 A66];

b11 = -sum(sum(weight .* Ix .* It));%w Ix It
b12 = -sum(sum(weight .* Iy .* It));%w Iy It
b13 = -sum(sum(xCoord .* weight .* Ix .* It));%x w Ix It
b14 = -sum(sum(yCoord .* weight .* Ix .* It));% y w Ix It
b15 = -sum(sum(xCoord .* weight .* Iy .* It));% x w Iy It
b16 = -sum(sum(yCoord .* weight .* Iy .* It));% y w Iy It

b = [b11;b12;b13;b14;b15;b16];

%x = A \ b;
x = pinv(A) * b;
nanIdx = find(isnan(x) == 1);
x(nanIdx) = zeros(size(nanIdx));
end

function r=iGetN(m,x,y,N)

[h,w,c]=size(m);
halfN = floor(N/2);
n1=halfN; n2=N-halfN-1;
r=zeros(N,N,c);
xmin=max(1,x-n1);
xmax=min(w,x+n2);
ymin=max(1,y-n1);
ymax=min(h,y+n2);
pxmin=halfN-(x-xmin)+1; pxmax=halfN+(xmax-x)+1;
pymin=halfN-(y-ymin)+1; pymax=halfN+(ymax-y)+1;
r(pymin:pymax,pxmin:pxmax,:)=m(ymin:ymax,xmin:xmax,:);
end
   

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/572320.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C语言自定义类型【结构体】

结构体的概念 结构是一些值的集合&#xff0c;这些值被称为成员变量。结构的每个成员可以是不同类型的变量。 1.结构体的声明 1.1普通声明 我们假设要创建一本书的类型&#xff0c;那我们需要书名&#xff0c;作者&#xff0c;价格&#xff0c;书的ID 代码如下&#xff1a;…

第十五届蓝桥杯省赛第二场C/C++B组A题【进制】题解(AC)

解题思路 按照题意进行模拟&#xff0c;计算 x x x 的 b b b 进制过程中&#xff0c;若出现余数大于 9 9 9&#xff0c;则说明 x x x 的 b b b 进制一定要用字母进行表示。 #include <iostream> #include <cstring> #include <algorithm> #include &l…

vue3推荐算法

Vue 3 推荐算法主要指的是在 Vue 3 框架中实现的或者适用于 Vue 3 的算法库或组件库。Vue 3 由于其优秀的设计和性能&#xff0c;被广泛应用于构建各种类型的应用程序&#xff0c;包括需要复杂算法支持的项目。以下是一些在 Vue 3 中可能会用到的推荐算法资源&#xff1a; Vue-…

啊? 又要洗数据啦!! 还是两个key决定一个表! 二维Map学习,基于guava的HashBasedTable

一个洗数据的需求&#xff0c;表设计的外建不能判断某一个数据源&#xff0c;还要根据tyoe来进行判断才可以。 那此时呆逼的查发能实现但不够优雅&#xff0c;于是乎想到了二维数组&#xff0c;查了下资料有相关的实现给大家分享下&#xff01;&#xff01; 背景 表设计如下&a…

美易官方:AI热潮“熄火”了?Meta Q1财报较差

近期&#xff0c;随着Meta&#xff08;前Facebook&#xff09;发布了其2023年第一季度的财报&#xff0c;一场科技股的震荡在美股市场上演。曾经风光无限的AI热潮似乎出现了“熄火”的迹象&#xff0c;引发了市场的广泛关注和讨论。 Cresset Wealth Advisors首席投资官Jack Abl…

libVLC 专栏介绍

本专栏主要界面libVLC的使用&#xff0c;详细介绍了相关用法&#xff0c;使用Qt作为显示界面&#xff0c;不仅可以了解Qt的使用&#xff0c;QSS的美化&#xff0c;更能够熟悉libVLC核心接口的使用&#xff0c;最后打造一款属于自己的精美播放器。 每一节都有单独的源码供查看。…

CSS @media 媒体查询全解:打造极致跨平台页面的动态户体体验

随着互联网设备的多样化和用户浏览习惯的变化&#xff0c;现代网页设计越来越注重提供跨平台、跨设备的无缝用户体验。CSS媒体查询media在此背景下扮演着至关重要的角色&#xff0c;它赋予网页设计者精准控制网页样式的能力&#xff0c;使之能随设备环境变化而动态调整&#xf…

内存管理下及模板初阶

嗨喽&#xff0c;今天阿鑫给大家带来内存管理下以及模板初阶的博客&#xff0c;下面让我们开始今天的学习吧&#xff01; 内存管理下及模板初阶 new和delete的实现原理定位new表达式(placement-new)常见面试题泛型编程函数模板类模板 1. new和delete的实现原理 1.1 内置类型…

短链接推荐:一个可以监测用户行为的“营销神器”

客户对我的推广有兴趣吗&#xff1f;他喜欢我的产品吗&#xff1f;他打开了我的营销信息吗&#xff1f;这三个问题相信每一位推广者都遇到过。接下来&#xff0c;就将给大家介绍一位大聪明——它能帮你监测每一位用户的行为&#xff0c;让你分分秒秒掌握用户的心理&#xff01;…

consul服务注册与发现、服务配置与刷新

为什么要用服务注册&#xff1f;为什么要用consul不用eureka&#xff1f; 举个栗子&#xff1a; 微服务当中存在多个服务模块&#xff0c;每个服务模块的ip端口在每套环境是不一致的&#xff0c;开发切换环境部署时&#xff0c;如果漏了一个配置忘记改动&#xff0c;将是一个很…

黑龙江—等保测评三级安全设计思路

需求分析 6.1、 系统现状 6.2、 现有措施 目前&#xff0c;信息系统已经采取了下述的安全措施&#xff1a; 1、在物理层面上&#xff0c; 2、在网络层面上&#xff0c; 3、在系统层面上&#xff0c; 4、在应用层面上&#xff0c; 5、在管理层面上&#xff0c; 6.…

数码摄影色彩构成,数码相机色彩管理

一、资料描述 本套摄影色彩资料&#xff0c;大小58.54M&#xff0c;共有6个文件。 二、资料目录 《抽象彩色摄影集》.阿瑟.pdf 《色彩构成》.pdf 《色彩学》.星云.扫描版.pdf 《摄影色彩构成》.pdf 《数码相机色彩管理》.pdf 数码摄影进阶之4《色彩篇》.pdf 三、资料下…

【PCL】教程narf_feature_extraction 如何从深度图像中提取 NARF 特征

如何从范围图像中提取 NARF 特征  本教程演示如何从深度图像中在 NARF 关键点位置提取 NARF 描述符。该可执行文件使我们能够从磁盘加载点云&#xff08;或创建它&#xff0c;如果没有提供&#xff09;&#xff0c;在其上提取兴趣点&#xff0c;然后在这些位置计算描述符。然…

spring @value @configurationProperties比较

今天项目中需要使用数组的方式 来加载一批 配置 yml: xxxx: - xxxxx - xsssss javaBean Value("${xxxxx.xxxxx}") private List<String> xxxs; 启动时候报错&#xff0c;无法加载&#xff0c;TM试验了1个小时&#xff0c;我一开始想到是格式的问题&#x…

Android 10.0 Launcher3替换桌面app图标后大小和其他app图标不一样的问题解决方案

1.前言 在10.0的系统ROM产品定制化开发中,在关于launcher3的产品定制化开发中,在有些时候需要对一些第三方的app图标做 替换或者是做一些动态图标的替换,发现在替换以后图标大小和其他app的图标大小不一样,所以就需要看是具体哪里 对app的图标做了缩放功能,接下来就需要去…

【注解和反射】类加载器

继上一篇博客【注解和反射】什么时候类会和不会被初始化&#xff1f;-CSDN博客 目录 六、类加载器 测试&#xff1a;获得类加载器 &#xff08;1&#xff09;如何获取Java中的类加载器及其父类加载器 &#xff08;2&#xff09;测试当前类是哪个类加载器 &#xff08;3&am…

【C++】STL-vector模拟实现

目录 1、vactor的模拟实现 1.1 成员变量 1.2 size、capacity 1.3 迭代器 1.4 构造、析构、拷贝构造、operator 1.5 push_back、pop_back、reserve 1.6 operator[] 1.7 insert、erase 1.8 resize 2、使用memcpy拷贝问题 1、vactor的模拟实现 1.1 成员变量 vector是顺…

时尚新选择,小塔RFID技术重塑样衣管理

在时尚领域&#xff0c;样衣是创意与工艺的完美结合&#xff0c;每一件都承载着设计师的心血与期待。然而&#xff0c;当这些珍贵的样版在传统的管理体系下流转时&#xff0c;样版管理成为一个令人头疼的问题。手动记录、盘点和样板追溯成为常态&#xff0c;但这种方式容易出错…

机器学习(二)之监督学习

前言&#xff1a; 上一节大概讲解了几种学习方式&#xff0c;下面几张就具体来讲讲监督学习的几种算法。 以下示例中和都是权重的意思&#xff01;&#xff01;&#xff01; 注&#xff1a;本文如有错误之处&#xff0c;还请读者指出&#xff0c;欢迎评论区探讨&#xff01; 1…

17. map和set的模拟实现(也就是用红黑树封装map和set)

1.map和set底层调用的红黑树的实现 有不清楚的地方&#xff0c;参考AVL树的模拟实现和红黑树的模拟实现 红黑树迭代器的实现 // 红黑树迭代器的类模板 template<class T, class Ref, class Ptr> struct __RBTreeIterator {// 将红黑树节点的类类型定义为Nodetypedef R…
最新文章