【问题标题】:How can i pass structs across files by value如何按值跨文件传递结构
【发布时间】:2017-07-26 21:21:36
【问题描述】:

我能够生成一段可编译的代码,将结构传递给函数,但是当我尝试使用“按值传递”时,我的代码就崩溃了。

我已经研究了如何在多个文件中使用相同的格式化结构,但我不确定在按值传递函数时是否有任何不同?

注意:这是在 arduino IDE 中用 C++ 编写的

我的地址传递代码如下:

passingStructs.ino

#include "a.h"
#include "b.h"

myStruct volatile structure1;

void setup() {

}

void loop() {


  structure1.foo = 7;
  structure1.bar = 11;

  int lower = minusData(&structure1);
  int higher = addData(&structure1);
}

啊.h

#include "b.h"

#ifndef __a_h
#define __a_h

//prototype functions
int addData(struct myStruct *structureC);

#endif //__a_h

a.cpp:

#include "a.h"
#include "b.h"

int addData(struct myStruct *structureC) {

  int x = structureC->foo;
  int y = structureC->bar;

  return (x + y);
}

b.h:

#ifndef __b_h
#define __b_h

//Define structure
typedef struct myStruct {
  int foo;
  int bar;
};

//Prototype functions
int minusData(struct myStruct *structureC);

#endif //__b_h

b.cpp:

#include "b.h"

myStruct structureC;

    int minusData(struct myStruct *structureC) {
      int x = structureC->foo;
      int y = structureC->bar;

      return (x - y);
    }

但是,如果我使用 int 更高 = addData(structure1); 在 .ino 文件中和

int addData(struct myStruct structureC) {

  int x = structureC.foo;
  int y = structureC.bar;

  return (x + y);
}

在头文件中具有相同原型的a.cpp文件中,编译器拒绝代码说

no matching function for call to ‘myStruct::myStruct(volatile myStruct&)’

有什么想法吗?

【问题讨论】:

  • __a_h 是为实现保留的标识符。通过定义它,你谴责你的程序有未定义的行为。
  • 这个问题好像和C语言没有关系。
  • 您的a.h 是否有addData 的按值重载原型?
  • 错误消息表明编译器正在为 myStruct 结构寻找构造函数,该结构引用 myStruct 类型对象。这段代码在使用typedef时有点乱码。看起来您正在尝试编写 C 源代码但使用 .cpp 文件,因此编译器将其视为 C++ 而不是 C。
  • @RichardChambers 我已将文件更改为 .c 而不是 .cpp。但是我仍然不确定如何使用 typedef 来减少你所说的“乱码”?

标签: c++ struct


【解决方案1】:

C++ 将为结构和类生成默认构造函数和复制运算符。

对于您的 myStruct,这些隐式函数将是:

struct myStruct {

  myStruct() {}                                // <-- implicit default constructor.

  myStruct(const myStruct& other)              // <-- implicit copy contructor
  {
     foo = other.foo;
     bar = other.bar;
  }

  myStruct& operator = (const myStruct& other) // <-- implicit copy operator
  {
     foo = other.foo;
     bar = other.bar;
     return *this;
  }

  int foo;
  int bar;
};

请注意,复制构造函数和运算符需要const myStruct&amp; 参数。 myStruct volatile structure1; 定义中的 volatile 关键字可防止参数匹配。

您必须显式声明一个接受const volatile myStruct&amp; 的复制运算符和/或构造函数才能使您的代码编译。

volatile 数据需要编译器的优化器进行特殊处理。这就是volatile 关键字在这里很重要的原因。你真的应该考虑你的数据是否真的需要这个限定符。在 Arduino 上,只有一种情况需要该关键字,即数据被中断程序修改

或者,您可以定义接受可变引用或指向数据的指针的函数:

struct MyStruct   // I suggest you use this syntax for declarting structures
{                 // So you don't ghave to repeat the struct keyword everywhere.
    myStruct(const myStruct& other)
    {
       foo = other.foo;
       bar = other.bar;
    }
    myStruct(const volatile myStruct& other)
    {
       foo = other.foo;
       bar = other.bar;
    }
    int foo, bar;
};

int addData(volatile const myStruct* structureC) 
{
  return structureC->foo + structureC->bar;
}

int addData(volatile const myStruct& structureC) 
{
  return structureC.foo + structureC.bar;
}

int addDataByCopy(myStruct structureC) 
{
  return structureC.foo + structureC.bar;
}

// ...
volatile myStruct my;
void loop()
{
   my.foo = 1;
   my.bar = 1;
   int x = addData(my);  // by const reference.
   // or
   int y = addData(&my); // by pointer.
   // or
   int z = addDataByCopy(my); // by copy
}

【讨论】:

  • 这真的很有用!但是,您能否提供一个示例,说明我如何将结构以“按值传递”和“按地址传递”格式传递给函数?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-03-04
  • 2011-02-14
  • 2015-01-21
  • 1970-01-01
  • 2012-09-20
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多