Simple UDP communication between Simulink and Python

Keywords: Python socket MATLAB

UDP communication between Simulink and Python

This paper summarizes the recent tasks, uses UDP to realize the communication between simulink and python, and focuses on the code of the Python udp receiver (see for the usage of python socket Previous: basic usage of socket module in python)

In fact, the principle of this task is very direct. First, localhost is used as the IP address, port customization (1024 ~ 65535) uses Simulink's built-in UDP sending module to send signals (in this paper, discrete sine signals are used) to python receiver.

Simulink block diagram

Import python struct module:

By default, the data from Simulink is in double format, so you need to add code to Python to decode the double data type. The double data type in MALTAB is the same as that in C, so Python's built-in struct library will be very effective.

The purpose of struct module is to transform the struct data structure of C into the type that Python can recognize when Python communicates with C program. In this case, the double type of MATLAB is unpacked. The corresponding statement is: recv ﹣ MSG ﹣ decode = struct.unpack ("d", recv ﹣ MSG) [0]. Here, recv ﹣ MSG is the original signal (bytes type) received by the python program. Struct.unpack ("d", recv ﹣ MSG) means to unpack recv ﹣ MSG with "d"(double type), and return a value with only one tuple. The first number is the decoded value.

Display received data in cmd:

After receiving the data, use matplotlib to draw the following figures:

Full python code

#!/usr/bin/env python    
# -*- coding: utf-8 -*

import socket, struct, os
import numpy as np
import matplotlib.pyplot as plt


def main():	
	# -------------------------------- Initializing --------------------------------------------
	# Create a socket
	udp_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
	# Bind the IP address and port.  
	localaddr = ("127.0.0.1", 54320)
	udp_socket.bind(localaddr)
	# Create an increment for while loop
	count = 0
	# Create a list to restor the data from simulink.
	data_collect = []
	# Create a path to save figure:
	path = 'Your Path Here'

	print("Please open the Simulink file under the current working directory")
	print("The program is waiting until you run the Simulink file.")

	#----------------------------------- Data Receiving ----------------------------------------
	# Using a loop to receive data from Simulink
	while count < 101: # Can be modified by (simulationTime/sampleTime).
		# Start to receive data from Simulink.
		recv_data = udp_socket.recvfrom(1024)
		#print(recv_data)
		# recv_data will return tuple, the first element is DATA, and the second is address information
		recv_msg = recv_data[0]
		send_addr = recv_data[1]
		# Decode the data from Simulink whose type is double and return a tuple
		recv_msg_decode = struct.unpack("d", recv_msg)[0]
		# Restore the data to a list:
		data_collect.append(recv_msg_decode)
		# Set the condition to jump out of this loop ???
		# Print the address information and the received data
		print("Number from MATLAB %s is : %s" % (str(send_addr), recv_msg_decode))
		count += 1
	# Close the udp socket.
	udp_socket.close()

	# ------------------------------------ Visualization ----------------------------------------------- 
	# Set the time axis, 10 is the simulation end time that can be modified by user.
	index = list(np.linspace(0, 10, (len(data_collect))))
	plt.plot(index, data_collect)
	plt.title("Signal Received from Simulink")
	plt.xlabel("Time")
	plt.ylabel("Received Data")
	plt.savefig(os.path.join(path, 'data_figure.png'), dpi=600)
	print("Close the figure to restart.")
	plt.show()

if __name__ == "__main__":
	main()

(the part of the loop in the code needs to be improved. Here we use the total (simulation time / sampling time) + 1 to get the parameters after while.)

33 original articles published, 36 praised, 20000 visitors+
Private letter follow

Posted by tommmmm on Tue, 04 Feb 2020 02:30:07 -0800