You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
105 lines
3.2 KiB
C#
105 lines
3.2 KiB
C#
using System;
|
|
using System.Runtime.InteropServices;
|
|
using System.Text;
|
|
|
|
namespace GeoSigmaDrawLib
|
|
{
|
|
/// <summary>
|
|
/// 内存管理辅助类
|
|
/// </summary>
|
|
public static class MarshalHelper
|
|
{
|
|
/// <summary>
|
|
/// 将 string 转成 C++ 内存数据后调用 func
|
|
/// </summary>
|
|
/// <typeparam name="T">返回值类型</typeparam>
|
|
/// <param name="data">要数据的字符串</param>
|
|
/// <param name="func">被调用的业务函数</param>
|
|
/// <returns>返回 func 的返回值</returns>
|
|
public static T Call<T>(string data, Func<IntPtr, int, T> func)
|
|
{
|
|
IntPtr pBuff = IntPtr.Zero;
|
|
|
|
try
|
|
{
|
|
pBuff = Marshal.StringToHGlobalAnsi(data);
|
|
int nLen = Encoding.Default.GetByteCount(data);
|
|
return func(pBuff, nLen);
|
|
}
|
|
finally
|
|
{
|
|
if (pBuff != IntPtr.Zero)
|
|
{
|
|
Marshal.FreeHGlobal(pBuff);
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 将 string 转成 C++ 内存数据后调用 action
|
|
/// </summary>
|
|
/// <param name="data">要数据的字符串</param>
|
|
/// <param name="action">被调用的业务函数</param>
|
|
public static void Execute(string data, Action<IntPtr, int> action)
|
|
{
|
|
IntPtr pBuff = IntPtr.Zero;
|
|
|
|
try
|
|
{
|
|
pBuff = Marshal.StringToHGlobalAnsi(data);
|
|
int nLen = Encoding.Default.GetByteCount(data);
|
|
action(pBuff, nLen);
|
|
}
|
|
finally
|
|
{
|
|
if (pBuff != IntPtr.Zero)
|
|
{
|
|
Marshal.FreeHGlobal(pBuff);
|
|
}
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// 将 C++ 内存转换为 string
|
|
/// </summary>
|
|
/// <param name="pBuff">C++ 内存对应的 IntPtr</param>
|
|
/// <returns>当前 pBuff 为 IntPtr.Zero 时,返回空字符串,否则返回对应的字符串</returns>
|
|
public static string ToString(IntPtr pBuff)
|
|
{
|
|
if (pBuff == IntPtr.Zero)
|
|
{
|
|
return string.Empty;
|
|
}
|
|
|
|
string strData = Marshal.PtrToStringBSTR(pBuff);
|
|
Marshal.FreeBSTR(pBuff);
|
|
return strData;
|
|
}
|
|
|
|
/// <summary>
|
|
/// 将 C++ 的 double 数组(double *,并且必须是 new[]) 转换为 C# 的 double 数组
|
|
/// </summary>
|
|
/// <param name="pData">double *</param>
|
|
/// <param name="length">元素个数</param>
|
|
/// <returns>double[]</returns>
|
|
public static double[] ToDoubleArray(IntPtr pData, int length)
|
|
{
|
|
if (pData == IntPtr.Zero)
|
|
{
|
|
throw new ArgumentException($"{nameof(pData)} cannot be equal to IntPtr.Zero");
|
|
}
|
|
|
|
if (length <= 0)
|
|
{
|
|
throw new ArgumentOutOfRangeException(nameof(length), "Length must be greater than zero.");
|
|
}
|
|
|
|
double[] result = new double[length];
|
|
Marshal.Copy(pData, result, 0, length);
|
|
GeoSigmaLib.PointerArrayDelete(pData);
|
|
|
|
return result;
|
|
}
|
|
}
|
|
}
|