java - 在计算机之间发送图像(从 Java 到 MATLAB)

标签 java matlab udp client-server file-transfer

我试图将图像文件从一台 PC(客户端)发送到另一台运行 MATLAB 的 PC(服务器),但输出图像为空。

从不同的讨论中,我了解到主要问题是 Java 和 MATLAB 之间的一些“图像矩阵不匹配”。但是,我并不完全理解这个问题。

如果您能给我一些建议,我将不胜感激。

客户端Java代码:

import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;

import javax.imageio.ImageIO;

public class myclientimage 
{
    public static void main(String args[]) throws IOException
    {
         BufferedImage img = ImageIO.read(new File("D:\\zzz.jpg"));
         ByteArrayOutputStream baos = new ByteArrayOutputStream();        
         ImageIO.write(img, "jpg", baos);
         baos.flush();
         byte[] buffer = baos.toByteArray();

         DatagramSocket clientSocket = new DatagramSocket();       
         InetAddress IPAddress = InetAddress.getByName("192.168.0.102");
         System.out.println(buffer.length);

         DatagramPacket packet = new DatagramPacket(buffer, buffer.length, IPAddress, 9091);

         clientSocket.send(packet);

         System.out.println("aaaa");
    }

}

服务器 MATLAB 代码:

udpA=udp('192.168.0.104', 9090,'LocalPort', 9091);
fopen(udpA);
A = fread(udpA, 200000);

du = reshape(A,size(A)); % converting vector du to 3d Image array 
imwrite(uint8(du), 'du.jpg'); %save our du to file du.jpg
I = imread('du.jpg'); %test if it saved correctly
imshow(I); 

fclose(udpA);

最佳答案

好的,这就是解决方案。首先需要澄清一些事情,我们将图像作为压缩的 jpeg 发送,而不是作为独立像素发送。因此imwrite不能用于此目的,因为它需要图像输入(3D 数组)。那么你应该使用fwrite相反。

另一个(小)问题是读取 BufferedImage你所做的方式会给你一个不同的大小,我想你在打印 buffer.length 时注意到了这一点并且得到的尺寸与您的计算机报告的尺寸不同。可以找到此问题的解决方案in the second answer of this question 。然而,这对图像没有影响(可能会降低质量?)无论是否使用链接中提到的解决方案,传输都对我有效。

正如您在评论中提到的,您收到了 512 个 double 。所以基本上需要做三件事:

  1. 增加InputBufferSize您的 UDP 对象(默认 512 字节)。
  2. 增加InputDatagramPacketSize UDP 对象的大小(默认 8KB),除非您不希望文件大于此大小,否则您将以 block 的形式发送文件。
  3. 将 double 转换为 uint8,因为这就是您接收它们的方式。

最终的Java代码:

public class SendImageUDP {
  public static void main(String args[]) throws IOException {
    BufferedImage img = ImageIO.read(new File("your_pic.jpg"));
    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    ImageIO.write(img, "jpg", baos);
    baos.flush();
    byte[] imageBuffer = baos.toByteArray();
    System.out.println(imageBuffer.length);

    InetAddress IPAddress = InetAddress.getByName("127.0.0.1"); // LocalHost for testing on the same computer
    DatagramSocket clientSocket = new DatagramSocket(9090, IPAddress); // Specify sending socket

    DatagramPacket packet = new DatagramPacket(imageBuffer, imageBuffer.length, IPAddress, 9091);
    clientSocket.send(packet);

    System.out.println("data sent");
    clientSocket.close();
  }
}

最终的 MATLAB 代码:

clear
close all

%% Define computer-specific variables

ipSender = '127.0.0.1'; % LocalHost for testing on the same computer
portSender = 9090;

ipReceiver = '127.0.0.1'; % LocalHost for testing on the same computer
portReceiver = 9091;

%% Create UDP Object

udpReceiver = udp(ipSender, portSender, 'LocalPort', portReceiver);
udpReceiver.InputBufferSize = 102400; % 100KB to be safe
udpReceiver.InputDatagramPacketSize = 65535; % Max possible

%% Connect to UDP Object

fopen(udpReceiver);
[A, count] = fread(udpReceiver, 102400, 'uint8'); % Receiving in proper format, big size just to be safe
A = uint8(A); % Just making sure it worked correctly

fileID = fopen('du.jpg','w'); % Save as a JPEG file because it was received this way
fwrite(fileID, A);
I = imread('du.jpg'); % Test if it saved correctly
imshow(I); 

%% Close

fclose(udpReceiver);
delete(udpReceiver);

从 MATLAB 代码中可以看出,接收到的数据不需要重新整形,因为它已经是压缩的 JPEG 数据,无论如何重新整形都没有意义。只需将其写入文件即可。

来源:

关于java - 在计算机之间发送图像(从 Java 到 MATLAB),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38255357/

相关文章:

Java:部署.war文件时执行方法

java - 捕获 Java 小程序取消按钮

java - Android:无法找到代码中的错误?

matlab:如果用户按下关闭按钮,则关闭图形用户界面

java - java中的UDP套接字聊天应用

c++ - UDP 客户端/服务器程序,通过不同 IP 和端口上的 2 个套接字进行通信

java - Java 中的 Google snappy 压缩实现

matlab - 使用递归 MATLAB 计算斐波那契数列的总和

matlab - 我正在尝试编写代码以将传输信号与接收信号交叉关联以确定样本延迟数

udp - "Address already in use": I'm misunderstanding UDP