假设我有一个char*类型的指针到unicode字符串,我知道长度:
char* _unmanagedStr;
int _unmanagedStrLength;
Run Code Online (Sandbox Code Playgroud)
我有2种方法将其转换为.NET字符串:
Marshal.PtrToStringUni((IntPtr)_unmanagedStr, _unmanagedStrLength);
Run Code Online (Sandbox Code Playgroud)
和
new string(_unmanagedStr, 0, _unmanagedStrLength);
Run Code Online (Sandbox Code Playgroud)
在我的测试中,两个调用都给出了完全相同的结果,但它new string()比1.8倍快Marshal.PtrToStringUni().
为什么这种性能差异?两者之间还有其他功能差异吗?
我需要在我的C#应用程序中使用这个枚举,但它不会让我使用这些值.当我将类型指定为uint时,我可以使用-1值,当我指定int时,我不能使用最后2个值.有没有办法在这里使用unchecked关键字来允许我定义所有这些值?这些值来自外部源,因此我无法更改它们.
internal enum MyValues : int
{
value1 = -1,
value2 = 0,
value3 = 0x80000000,
value4 = 0xFFFFFFFF
}
Run Code Online (Sandbox Code Playgroud) 我正在尝试使用C#为学校项目创建缓冲区溢出:
unsafe
{
fixed (char* ptr_str = new char[6] {'H', 'a', 'l', 'l', 'o', ','})
{
fixed (char* ptr_str2 = new char[6] {'W', 'e', 'r', 'e', 'l', 'd'})
{
fixed (char* ptr_str3 = new char[6] {'!', '!', '!', '!', '!', '!'})
{
for (int i = 0; i < 8; i++)
{
ptr_str2[i] = 'a';
}
for (int i = 0; i < 6; i++)
{
this.Label2.Text += ptr_str[i];
this.Label3.Text += ptr_str2[i];
this.Label4.Text += ptr_str3[i];
}
}
}
}
} …Run Code Online (Sandbox Code Playgroud) 我正在努力理解sun.misc.Unsafe的文档 - 我想因为它不适合一般用途,没有人真的为让它可读而烦恼 - 但实际上我真的需要一种方法来找到一个元素的地址一个数组(以便我可以将指针传递给本机代码).有没有人有任何工作代码这样做?它可靠吗?
我在msdn上遇到了以下代码:
unsafe static void SquarePtrParam (int* p)
{
*p *= *p;
}
unsafe static void Main()
{
Point pt = new Point();
pt.x = 5;
pt.y = 6;
// Pin pt in place:
fixed (int* p = &pt.x)
{
SquarePtrParam (p);
}
// pt now unpinned.
Console.WriteLine ("{0} {1}", pt.x, pt.y);
}
Run Code Online (Sandbox Code Playgroud)
我只是想知道,我们是直接访问SquarePtrParam函数中的指针,它是否继承了从调用方法修复数组的信息?
为什么我们不需要将其明确地设置为fixed本地SquarePtrParam.
我想我可以对这个fixed陈述进行一些阐述.
我正在尝试提出一个解决方案,以便我如何将C#中的数组数组传递给本机函数.我已经有了一个函数委托(Marshal.GetDelegateForFunctionPointer),但现在我正在尝试将多维数组(或者更确切地说是一个数组数组)传递给它.
当输入有2个子数组时,此代码示例有效,但我需要能够处理任意数量的子数组.您能想到的最简单的方法是什么?我不想在数组之间复制数据,因为这将在实时循环中发生(我正在与音频效果通信)
public void process(float[][] input)
{
unsafe
{
// If I know how many sub-arrays I have I can just fix them like this... but I need to handle n-many arrays
fixed (float* inp0 = input[0], inp1 = input[1] )
{
// Create the pointer array and put the pointers to input[0] and input[1] into it
float*[] inputArray = new float*[2];
inputArray[0] = inp0;
inputArray[1] = inp1;
fixed(float** inputPtr = inputArray)
{
// C function signature is someFuction(float** input, …Run Code Online (Sandbox Code Playgroud) 我有一个关于静态源代码分析的大型项目,一切都成功编译,除了一件事.我在标题中提供了错误消息.令我困惑的一点是,它给出了一条错误信息,说不安全.我认为应该只是警告,而不是错误.顺便说一下,我正在使用Visual Studio 2012.这是我在ctime中得到错误的代码的一部分.如果有人能帮助我克服这个错误,我会很高兴.
void CppCheckExecutor::reportProgress(const std::string &filename, const char stage[], const std::size_t value)
{
(void)filename;
if (!time1)
return;
// Report progress messages every 10 seconds
const std::time_t time2 = std::time(NULL);
if (time2 >= (time1 + 10)) {
time1 = time2;
// current time in the format "Www Mmm dd hh:mm:ss yyyy"
const std::string str(std::ctime(&time2));
// format a progress message
std::ostringstream ostr;
ostr << "progress: "
<< stage
<< ' ' << value << '%';
if (_settings->_verbose)
ostr << " time=" …Run Code Online (Sandbox Code Playgroud) 在MSDN文章中,它提到了启用fp:fast模式时,添加标识(a±0.0 = a,0.0-a = -a)等操作是不安全的.a+0 != a在这种模式下有什么例子吗?
编辑:正如下面提到的那样,这种问题通常在进行比较时出现.我的问题来自比较,psedocode如下所示:
for(i=0;i<v.len;i++)
{
sum+=v[i];
if( sum >= threshold) break;
}
Run Code Online (Sandbox Code Playgroud)
添加0(v[i])值后它会中断.在v[i]从计算不是,它被分配.我知道如果我v[i]是从计算开始,那么舍入可能会发挥作用,但为什么即使我给出v[i]零值,我仍然有这个sum < threshold但是sum + v[i] >= threshold?
直到现在我才认为 Marshal.SizeOf 是计算非托管堆上 blittable 结构的内存大小的正确方法(这似乎是 SO 上的共识以及网络上几乎所有其他地方的共识)。
但是在阅读了一些针对 Marshal.SizeOf 的警告之后(这篇文章在“但是有一个问题......”之后)我尝试了一下,现在我完全困惑了:
public struct TestStruct
{
public char x;
public char y;
}
class Program
{
public static unsafe void Main(string[] args)
{
TestStruct s;
s.x = (char)0xABCD;
s.y = (char)0x1234;
// this results in size 4 (two Unicode characters)
Console.WriteLine(sizeof(TestStruct));
TestStruct* ps = &s;
// shows how the struct is seen from the managed side... okay!
Console.WriteLine((int)s.x);
Console.WriteLine((int)s.y);
// shows the same as before (meaning that -> is based …Run Code Online (Sandbox Code Playgroud) 这是脱离上下文所以它看起来有点奇怪,但我有以下数据结构:
use std::marker::PhantomData;
pub struct Map<T, M=()> {
data: Vec<T>,
_marker: PhantomData<fn(M) -> M>,
}
Run Code Online (Sandbox Code Playgroud)
Map是一个关联映射,其中键被"标记"以防止在另一个不相关的映射上使用来自一个映射的键.用户可以通过传递他们制作的一些独特类型来选择M,例如:
struct PlayerMapMarker;
let mut player_map: Map<String, PlayerMapMarker> = Map::new();
Run Code Online (Sandbox Code Playgroud)
这一切都很好,但是我想为这个地图编写的一些迭代器(例如只提供值的迭代器)在它们的类型中不包含标记.以下转化是否可以安全地丢弃标记?
fn discard_marker<T, M>(map: &Map<T, M>) -> &Map<T, ()> {
unsafe { std::mem::transmute(map) }
}
Run Code Online (Sandbox Code Playgroud)
这样我就可以编写和使用:
fn values(&self) -> Values<T> {
Values { inner: discard_marker(self).iter() }
}
struct Values<'a, T> {
inner: Iter<'a, T, ()>,
}
Run Code Online (Sandbox Code Playgroud)