简体   繁体   English

如何将整数数组从经典asp传递到ac#COM对象?

[英]How do I pass an array of integers from classic asp to a c# COM object?

I'm trying to pass an array of integers from Classic ASP to a DLL created in C#. 我正在尝试将经典数组中的整数数组传递给用C#创建的DLL。

I have the following C# method: 我有以下C#方法:

public int passIntArray(object arr)
{
    int[] ia = (int[])arr;
    int sum = 0;
    for (int i = 0; i < ia.Length; i++)
        sum += ia[i];

    return sum;
}

I've tried a number of ways to convert arr to an int[], but not having any success. 我尝试了多种方法将arr转换为int [],但没有成功。 My asp code is: 我的asp代码是:

var arr = [1,2,3,4,5,6];
var x = Server.CreateObject("dllTest.test");
Response.Write(x.passIntArray(arr));

I am currently getting the following error: 我目前收到以下错误:

Unable to cast COM object of type 'System.__ComObject' to class type 'System.Int32[]'. Instances of types that represent COM components cannot be cast to types that do not represent COM components; however they can be cast to interfaces as long as the underlying COM component supports QueryInterface calls for the IID of the interface.

Can anyone tell me how to do it or tell me it can't be done? 谁能告诉我该怎么做还是不能做到?

Using the code on this very useful page http://www.add-in-express.com/creating-addins-blog/2011/12/20/type-name-system-comobject/ I have managed to find out that the type of the passed parameter is "JScriptTypeInfo" if that's of any use. 使用此非常有用的页面上的代码http://www.add-in-express.com/creating-addins-blog/2011/12/20/type-name-system-comobject/我设法找出了如果有任何用处,则传递的参数的类型为“ JScriptTypeInfo”。

If I add: 如果我添加:

foreach (object m in arr.GetType().GetMembers())
    // output m

I get the following output: 我得到以下输出:

System.Object GetLifetimeService()
System.Object InitializeLifetimeService()
System.Runtime.Remoting.ObjRef CreateObjRef(System.Type)
System.String ToString()
Boolean Equals(System.Object)
Int32 GetHashCode()
System.Type GetType()

As explained in the SO item I suggested was a duplicate , you would change your ASP code thus: 我建议SO项目中所述 ,它是重复的 ,因此您可以更改ASP代码:

function getSafeArray(jsArr) 
{
  var dict = new ActiveXObject("Scripting.Dictionary");     
  for (var i = 0; i < jsArr.length; i++)     
    dict.add(i, jsArr[i]);     
  return dict.Items(); 
} 
var arr = [1,2,3,4,5,6]; 
var x = Server.CreateObject("dllTest.test"); 
Response.Write(x.passIntArray(getSafeArray(arr))); 

You should also change your C# method signature to: 您还应该将C#方法签名更改为:

public int passIntArray(object[] arr) // EDITED: 17-Sept

or 要么

public int passIntArray([MarshalAs(UnmanagedType.SafeArray, SafeArraySubType=VarEnum.VT_I4)]  int[] arr)

The point is that you are not really trying to go from JavaScript to C#, you are going from JavaScript to COM: you can only interface the C# DLL at all because it is ComVisible and is registered in the COM registry with a ProgID which Server.CreateObject can look up. 关键是您并不是真正想从JavaScript转到C#,而是从JavaScript转到COM:根本只能连接C#DLL,因为它是ComVisible,并且已在Pro Server.CreateObject注册了ProgID Server.CreateObject可以查找。 With the signature change, your DLL's COM-exposed interface will expect to receive an unmanaged SAFEARRAY and the script code above is a way to get JavaScript to provide one, using the COM Scripting.Dictionary as a sort of custom marshaler. 更改签名后,您的DLL的COM公开界面将有望收到不受管理的SAFEARRAY,并且上述脚本代码是使用COM Scripting.Dictionary作为一种自定义封送处理程序的一种使JavaScript提供脚本的方法。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM