📄 moveint.c
字号:
/* * MOVEINT A SIMULINK moving integration * * Syntax: [sys, x0] = sbuffer(t, x, u, flag, In_length, Time_window, Sample_time, Method) * * In-length: the vector length of the input vector. * Time_window: int_t^(t+T) f(x) dx, the scale T, window size of the integration. * Sample_time: sampling time of the integration. This is a discrete-time block. * Method: integration method. Could be choose from: forward, backward, first_order. * * Wes Wang Dec. 8, 1994 * Copyright (c) 1994-96 by The MathWorks, Inc. * All Rights Reserved * $Revision: 1.1 $ $Date: 1996/04/01 19:03:36 $ */#define S_FUNCTION_NAME moveint#ifdef MATLAB_MEX_FILE#include <stdio.h> /* needed for declaration of sprintf */#include "mex.h" /* needed for declaration of mexErrMsgTxt */#endif/* * need to include simstruc.h for the definition of the SimStruct and * its associated macro definitions. */#include "simstruc.h"/* * Defines for easy access of the input parameters */#define NUM_ARGS 4#define IN_LENGTH ssGetArg(S,0)#define TIME_WINDOW ssGetArg(S,1)#define SAMPLE_TIME ssGetArg(S,2)#define METHOD ssGetArg(S,3)/* * mdlInitializeSizes - called to initialize the sizes array stored in * the SimStruct. The sizes array defines the * characteristics (number of inputs, outputs, * states, etc.) of the S-Function. */static void mdlInitializeSizes(S) SimStruct *S;{ /* * Set-up size information. */ if (ssGetNumArgs(S) == NUM_ARGS) { int in_length, num_points; char method[2];/* char err_msg[256]; */ if ((mxGetN(IN_LENGTH) != 1) || (mxGetM(IN_LENGTH) != 1)) {#ifdef MATLAB_MEX_FILE mexErrMsgTxt("The inout vector length must be a scalar");#endif } if ((mxGetN(TIME_WINDOW) != 1) || (mxGetM(TIME_WINDOW) != 1)) {#ifdef MATLAB_MEX_FILE mexErrMsgTxt("The integration time window must be a scalar");#endif } if ((mxGetN(SAMPLE_TIME)*mxGetM(SAMPLE_TIME) != 1) && (mxGetN(SAMPLE_TIME)*mxGetM(SAMPLE_TIME) != 2)) {#ifdef MATLAB_MEX_FILE mexErrMsgTxt("The sample time must be a scalar or a vector of length 2");#endif } if (mxGetM(METHOD) != 1) {#ifdef MATLAB_MEX_FILE mexErrMsgTxt("Integration method must be a string");#endif } in_length = mxGetPr(IN_LENGTH)[0]; num_points = (int)(mxGetPr(TIME_WINDOW)[0] / mxGetPr(SAMPLE_TIME)[0] + 0.49) + 1; if (num_points <= 2) {#ifdef MATLAB_MEX_FILE mexErrMsgTxt("The integration time window must be greater than sample time.");#endif } else if (in_length < 1) {#ifdef MATLAB_MEX_FILE mexErrMsgTxt("The input vector length must be a positive number.");#endif } method[0] = (char)mxGetPr(METHOD)[0]; method[1] = (char)mxGetPr(METHOD)[1]; ssSetNumContStates( S, 0); ssSetNumDiscStates( S, 0); ssSetNumInputs( S, in_length); ssSetNumOutputs( S, in_length); if ((method[0] == 'f') && (method[1] == 'o')) ssSetDirectFeedThrough(S, 0); else ssSetDirectFeedThrough(S, 1); ssSetNumInputArgs( S, NUM_ARGS); ssSetNumSampleTimes( S, 1); ssSetNumRWork( S, in_length*(num_points + 1) + 1); /* storage: t, points, last_integration_value */ ssSetNumIWork( S, 2); /* Total_points=num_points, current points */ ssSetNumPWork( S, 0);/* sprintf(err_msg, "Initialization num_points = %i, in_length = %i\n",num_points, in_length); mexPrintf(err_msg); */ } else {#ifdef MATLAB_MEX_FILE char err_msg[256]; sprintf(err_msg, "Wrong number of input arguments passed to S-function MEX-file.\n" "%d input arguments were passed in when expecting %d input arguments.\n", ssGetNumArgs(S) + 4, NUM_ARGS + 4); mexErrMsgTxt(err_msg);#endif }}/* * mdlInitializeSampleTimes - initializes the array of sample times stored in * the SimStruct associated with this S-Function. */static void mdlInitializeSampleTimes(S) SimStruct *S;{ double sampleTime, offsetTime; /* * Note, blocks that are continuous in nature should have a single * sample time of 0.0. */ sampleTime = mxGetPr(SAMPLE_TIME)[0]; if ((mxGetN(SAMPLE_TIME) * mxGetM(SAMPLE_TIME)) == 2) offsetTime = mxGetPr(SAMPLE_TIME)[1]; else offsetTime = 0.; ssSetSampleTimeEvent(S, 0, sampleTime); ssSetOffsetTimeEvent(S, 0, offsetTime);}/* * mdlInitializeConditions - initializes the states for the S-Function */static void mdlInitializeConditions(x0, S) double *x0; SimStruct *S;{ int in_length = mxGetPr(IN_LENGTH)[0]; int num_points = (int)(mxGetPr(TIME_WINDOW)[0] / mxGetPr(SAMPLE_TIME)[0] + 0.49) + 1; double *last_time = ssGetRWork(S); double *storage_point = ssGetRWork(S) + 1; double *integ_value = ssGetRWork(S) + in_length * num_points + 1; int *cur_point = ssGetIWork(S); int i; /* * Initialize all storage and integration values */ for (i = 0; i < in_length * (num_points + 1); i++) *storage_point++ = 0.; *last_time = -1; /* * IWork */ *cur_point++ = num_points; *cur_point = 0;}/* * mdlOutputs - computes the outputs of the S-Function */static void mdlOutputs(y, x, u, S, tid) double *y, *x, *u; SimStruct *S; int tid;{ int *num_points = ssGetIWork(S); int *cur_point = ssGetIWork(S)+1; int in_length = mxGetPr(IN_LENGTH)[0]; double *last_time = ssGetRWork(S); double *storage_point = ssGetRWork(S) + 1; double *integ_value = ssGetRWork(S) + (in_length * (*num_points) + 1); double sample_time = mxGetPr(SAMPLE_TIME)[0]; double current_time; int i; char method[2]; current_time = ssGetT(S); method[0] = (char)mxGetPr(METHOD)[0]; method[1] = (char)mxGetPr(METHOD)[1]; if (*num_points > 0) { if ((current_time - *last_time) > sample_time/1000000.) {/* char err_msg[256]; */ int increament, point_before, point_after; point_before = (*num_points + *cur_point - 1) % (*num_points); point_after = (*cur_point + 1) % (*num_points);/* sprintf(err_msg, "Output: num_points = %i, in_length = %i\n",*num_points, in_length); mexPrintf(err_msg); */ for (i=0; i<in_length; i++) { increament = (*num_points) * i;/* sprintf(err_msg, "cur_point = %i, point_before = %i, point_after %i, increament %i\n",*cur_point, point_before, point_after, increament); mexPrintf(err_msg); */ if ((method[0] == 'f') && (method[1] == 'o')) {/* sprintf(err_msg, "integ_value = %f, storage_before = %f, current_point = %f \n", integ_value[i], storage_point[point_before+increament], storage_point[*cur_point+increament]); mexPrintf(err_msg); */ integ_value[i] = integ_value[i] + (storage_point[point_before + increament] - storage_point[*cur_point + increament]) * sample_time; } else if ((method[0] == 'b') && (method[1] == 'a')) { integ_value[i] = integ_value[i] + (u[i] - storage_point[point_after + increament]) * sample_time; } else { integ_value[i] = integ_value[i] + (u[i] + storage_point[point_before + increament] - storage_point[(*cur_point) + increament] - storage_point[point_after + increament]) * sample_time / 2; } storage_point[(*cur_point) + increament] = u[i]; } *cur_point = point_after; *last_time = current_time; } else {/* char err_msg[256]; */ for (i=0; i<in_length; i++) { int increament; increament = (*num_points) * i;/* sprintf(err_msg, "\n cur_point = %i, increament %i\n",*cur_point, increament); mexPrintf(err_msg); */ if ((method[0] == 'f') && (method[1] == 'o')) { } else if ((method[0] == 'b') && (method[1] == 'a')) { integ_value[i] = integ_value[i] + (u[i] - storage_point[*cur_point + increament]) * sample_time; } else { integ_value[i] = integ_value[i] + (u[i] - storage_point[(*cur_point) + increament]) * sample_time / 2; } storage_point[(*cur_point) + increament] = u[i]; } } } for (i = 0; i<in_length; i++) y[i] = integ_value[i];}/* * mdlUpdate - computes the discrete states of the S-Function */static void mdlUpdate(x, u, S, tid) double *x, *u; SimStruct *S; int tid;{}/* * mdlDerivatives - computes the derivatives of the S-Function */static void mdlDerivatives(dx, x, u, S, tid) double *dx, *x, *u; SimStruct *S; int tid;{}/* * mdlTerminate - called at termination of model execution. */static void mdlTerminate(S) SimStruct *S;{}#ifdef MATLAB_MEX_FILE /* Is this file being compiled as a MEX-file? */#include "simulink.c" /* MEX-File interface mechanism */#else#include "cg_sfun.h" /* Code generation registration function */#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -