我正在尝试将一组存储在数组中的超声波传感器数据发送给一个函数,该函数执行右移位,并将第一个元素替换为99,然后将其带回主代码。但不幸的是,我不能将数组带回主代码并打印出来。请帮我解决这个问题。
*BTW我尝试做的是用传感器的最新值更新数组,并将其余的值左移,并在每次循环运行时保留数组中的最后一个元素。如果有更好的方法,也请提出来。
#include <stdio.h>
#include <stdlib.h>
int arrayShift(double *data,int count);
/*Ultrasonic Sensor data*/
const int trigP = 2; //D4 Or GPIO-2 of nodemcu
const int echoP = 0; //D3 Or GPIO-0 of nodemcu
long duration;
int distance;
int level;
int maxL=430;
/*************************************************/
void setup()
{
/*********************************************/
Serial.begin(9600);
while (!Serial);
/*Ultrasonic Sensor data*/
pinMode(trigP, OUTPUT); // Sets the trigPin as an Output
pinMode(echoP, INPUT); // Sets the echoPin as an Input
/*********************************************/
}
void loop()
{
/*Ultrasonic Sensor data*/
digitalWrite(trigP, LOW); // Makes trigPin low
delayMicroseconds(2); // 2 micro second delay
digitalWrite(trigP, HIGH); // tigPin high
delayMicroseconds(10); // trigPin high for 10 micro seconds
digitalWrite(trigP, LOW); // trigPin low
double data[] = {1,4,9,16,25,36,49,64,81,100,121,144,169,196,225,256,289,324,361,400};
duration = pulseIn(echoP, HIGH); //Read echo pin, time in microseconds
distance= duration*0.034/2; //Calculating actual/real distance
double temp;
int address;
level = maxL - distance; //Calculating waret level
Serial.print("Distance = "); //Output distance on arduino serial monitor
Serial.println(distance);
Serial.print("Duration = "); //Output distance on arduino serial monitor
Serial.println(duration);
/****************************************************/
/* Shifting and adding most recent data*/
Serial.println("before shift");
for (int i = 0; i <20; i++) {
Serial.print(data[i]);
Serial.println("");
address=arrayShift(data,20);
Serial.println("after shift");
for (int i = 0; i <20; i++) {
Serial.print(data[i]);
Serial.print("");
Serial.println(address);
Serial.println("check");
delay(3000); //Pause for 3 seconds and start measuring distance again
/*********************************************/
}
}
/************** Functions ***************************/
int arrayShift(double *data,int count)
{
double temp = *data;
double newData[20];
for(int x=0; x<count; x++) {
newData[x]=*data;
data++;
}
Serial.println("new data");
for (int i = 0; i <20; i++) {
Serial.print(newData[i]);
Serial.print("");
}
for (int i = 19; i >0; i--) {
newData[i] = data[i-1];
}
}
newData[0] = 99;
return *newData;
}发布于 2021-07-07 22:55:40
arrayShift可以就地修改数组:
void arrayShift(double *data, unsigned int count, double newval)
{
while (count >= 2)
{
data[count - 1] = data[count - 2];
count--;
}
if (count == 1)
{
data[0] == newval;
}
}示例调用:
arrayShift(data, 20, 99.0);发布于 2021-07-07 23:58:16
首先,您需要更改函数的返回类型。int arrayShift(double *data,int count)到double* arrayShift(double* data,int count),返回时需要返回指向数据的指针,因此使用return newData;代替return *newData;,另一个问题是,当您将数据复制到newData数组时
for(int x=0; x<count; x++){
newData[x]=*data;
data++;
}您递增指针,然后使用该指针。这意味着你正在访问你没有权限访问的内存。这里:
for (int i = 19; i >0; i--){
newData[i] = data[i-1];
}要解决此问题,需要使用temp变量作为指针
double *temp=data;
for(int x=0; x<count; x++){
newData[x]=*temp;
temp++;
}但是现在我们返回了newData数组,我们需要用malloc来分配内存,因为如果我们不这样做,那么函数一结束,内存就会被释放。所以这个double newData[20]需要变成这个double *newData=(double*)malloc(20*sizeof(double));或者更好的这个double *newData=(double*)malloc(count*sizeof(double));,但是现在我们引入了一个内存泄漏,需要在循环函数中处理。
完全修正的功能:
double* arrayShift(double *data,int count) {
double *temp = data;
double *newData=(double*)malloc(count*sizeof(double));
for(int x=0; x<count; x++){ //Copy main data to newData array
newData[x]=*temp;
temp++;
}
Serial.println("new data");
for (int i = 0; i <20; i++){
Serial.print(newData[i]);
Serial.print("");
}
for (int i = 19; i >0; i--){
newData[i] = data[i-1];
}
newData[0] = 99;
return newData;
}但另一个问题是,在您的主代码中,您使用相同的数据数组,而不是返回的数组。
address=arrayShift(data,20);
Serial.println("after shift");
for (int i = 0; i <20; i++){
Serial.print(data[i]);// old data
Serial.print("");
}要解决此问题,您需要首先将地址变量的类型从int address;更改为double* address=NULL;
if(address!=NULL){
free(address); //handle the memory leak
}
address=arrayShift(data,20);
Serial.println("after shift");
for (int i = 0; i <20; i++){
Serial.print(address[i]);// new data
Serial.print("");
}但是现在您需要将数据从地址数组复制到数据数组,这样就不会在free(address)之后丢失数据。因此,在这种情况下,下面的函数更有意义。
因此,如果您想要更改相同的数组,只需使用以下命令:
void arrayShift(double *data,int count) {
for (int i = 19; i >0; i--){
data[i] = data[i-1];
}
data[0] = 99;
}上面的函数右移你的主数据数组,而不需要返回它,你可以像这样在你的主代码中使用数据数组。在循环函数中:
arrayShift(data,20);
Serial.println("after shift");
for (int i = 0; i <20; i++){
Serial.print(data[i]);
Serial.print("");
}我还认为在arrayshift函数中有一个额外的括号。
https://stackoverflow.com/questions/68287926
复制相似问题