C++ 如何安全地将浮点*x转换为常量浮点*const*y?
我有一个函数C++ 如何安全地将浮点*x转换为常量浮点*const*y?,c++,pointers,constants,C++,Pointers,Constants,我有一个函数audioReceived(float*input,int-bufferSize,int-nChannels),其中我想从需要const-float*const*inputBuffers的库中调用一个函数 显然,castingconst float*const*inputBuffers=(const float*const*)输入编译,但这是一个糟糕的主意,会导致程序崩溃、小猫死亡等。没有人需要修改原始的浮点*输入,正在处理的是传入的音频数据 我该怎么做才对呢 编辑:这里还有一些代码
audioReceived(float*input,int-bufferSize,int-nChannels)
,其中我想从需要const-float*const*inputBuffers的库中调用一个函数
显然,castingconst float*const*inputBuffers=(const float*const*)输入
编译,但这是一个糟糕的主意,会导致程序崩溃、小猫死亡等。没有人需要修改原始的浮点*输入
,正在处理的是传入的音频数据
我该怎么做才对呢
编辑:这里还有一些代码。audioReceived
是:
void testApp::audioReceived (float * input, int bufferSize, int nChannels){
Vamp::RealTime rt = Vamp::RealTime::fromMilliseconds(ofGetSystemTime());
float const *const tmp[] = { input, 0 };
Vamp::Plugin::FeatureSet fs = myPlugin->process(tmp, rt);
}
库函数过程
实际上是在基类中定义的:
/**
* Process a single block of input data.
*
* If the plugin's inputDomain is TimeDomain, inputBuffers will
* point to one array of floats per input channel, and each of
* these arrays will contain blockSize consecutive audio samples
* (the host will zero-pad as necessary). The timestamp in this
* case will be the real time in seconds of the start of the
* supplied block of samples.
*
* If the plugin's inputDomain is FrequencyDomain, inputBuffers
* will point to one array of floats per input channel, and each
* of these arrays will contain blockSize/2+1 consecutive pairs of
* real and imaginary component floats corresponding to bins
* 0..(blockSize/2) of the FFT output. That is, bin 0 (the first
* pair of floats) contains the DC output, up to bin blockSize/2
* which contains the Nyquist-frequency output. There will
* therefore be blockSize+2 floats per channel in total. The
* timestamp will be the real time in seconds of the centre of the
* FFT input window (i.e. the very first block passed to process
* might contain the FFT of half a block of zero samples and the
* first half-block of the actual data, with a timestamp of zero).
*
* Return any features that have become available after this
* process call. (These do not necessarily have to fall within
* the process block, except for OneSamplePerStep outputs.)
*/
virtual FeatureSet process(const float *const *inputBuffers,
RealTime timestamp) = 0;
在实际标题中:
FeatureSet process(const float *const *inputBuffers, Vamp::RealTime timestamp);
我认为EXC\u BAD\u ACCESS
可能源于库函数想要一个零填充数组,而我没有给它一个。(a) 这听起来合理吗?如果是的话,是时候问一个不同的so问题了吗
感谢大家迄今为止的帮助,这非常有启发性/澄清性/教育性/有趣。做&input
对演员本身应该足够了。请注意,内部函数的参数是指向指针的指针
编辑:
要按照您对原始问题的评论中的要求获取以空结尾的输入缓冲区列表,您可以使用:
float const * const buffers[] = {input, 0};
不一样
float **
因此,将input
转换为inputBuffers
是行不通的
通常,从非常量到常量的转换是隐式的,您不需要做任何特殊的操作。你不能轻易地从常量转换为非常量。仔细想想,这是合乎逻辑的。语义在这里很重要。从参数名中,我可以猜测您要调用的函数接受多个缓冲区,因此它需要一个浮点指针数组(即数组数组)。因为您只有一个数组,所以需要创建一个包含原始指针的数组,并将其传递给函数
如果函数对要传递的数组长度(即缓冲区的数量)有一个单独的参数,则使用一元&
运算符获取地址并传递长度1就足够了,否则需要创建一个以null结尾的临时数组:
float const *const tmp[] = { input, 0 };
然后将其传递给函数。您需要向其传递一个浮点**
,即指向指向浮点指针的指针。const
s只是告诉您函数不会修改所指向的任何值
如果通道数nChannels
、每个通道的bufferSize
浮动数可能可变,则可以设置必要的存储,例如:
float **data = new float *[nChannels];
for (int c = 0; c < nChannels; ++c) {
data[c] = new float[bufferSize];
}
最后,不要忘记删除[]
成员指针以及之后的双指针
for (int c = 0; c < nChannels; ++c) {
delete[] data[c];
}
delete[] data;
(披露:我写的代码让提问者感到困惑)这没有多大意义。你从一个指向float的指针开始,你想从中得到一个指向float的指针,并插入大量常量。哈?为什么这甚至有一个c++
标签?这不是一个纯粹的C问题吗?老实说,当涉及到常量时,我也会问“嗯?”——但这是特征提取库想要的,我试图在开始重写库之前先给出它想要的。(这可能会导致更多的混乱,不管怎样,我的工作假设是编写代码的人比我知道的要多一些——虽然可能不比你们中的一些人多)。SBI:它也应用于C++,如果他在C++中编译,然后,该层对C++中有效的解决方案开放,而不是在C.@ CyyFub中:您绝对确信它是“代码> const浮标*const */COD>(更好的写入<代码>浮点const *const */COD>)。不仅仅是浮点常量*const
?是否确定已正确解释库函数的输入内容?文件上怎么说?可能就够了。这取决于调用的函数。我想可能是这样,但在运行时它是EXC\u BAD\u ACCESS
。@Kevin:我意识到我的答案不适用于这里(因为函数采用const char*float*
,而不是const float**
),所以我删除了它。如果@Juraj对他的答案进行空编辑,我可以删除我的否决票。如果库希望数组的最后一个元素为null
,这可能是不够的。这里的断言是危险的,不知道库的期望是什么。@Oli:我不明白你在这里的意思。转换本身是正确的。早在OP关于所需格式的说明之前,我就发布了答案。问题是关于演员的,我想我已经回答了。我可能会编辑answew。是的,我怀疑有类似的东西。然而,不知道,这一切只是猜测!OP应该阅读图书馆文档。@Tomalak,我是个好孩子,读过,但文档并不完全清楚/完整。考虑到它是开源的,我希望能对此有所帮助,但首先我必须弄清楚它是如何工作的@不,他是指他写的东西。你可能正在打另外一个球。我想我们已经达到了从有限的信息中可以告诉你的极限。实际上,我的意思是没有&
。更正。这是正确的,但有一些重要的警告。例如,您不能将t**
隐式转换为const t**
。没问题T**
不能隐式转换为T const**
但可以转换为T const*const*
。
for (int i = 0; i < bufferSize; ++i) {
for (int c = 0; c < nChannels; ++c) {
data[c][i] = input[i * nChannels + c];
}
}
myPlugin->process(data, rt);
for (int c = 0; c < nChannels; ++c) {
delete[] data[c];
}
delete[] data;
myPlugin->process(&input, rt);