我当前是stuck on a problem.,它要求打印某种商店库存管理的月销售额,然后要求用户输入1-12之间的数字以查看特定月份的总数。
自从我在Visual Studio中进行此操作(创建一个空白/空项目,因此没有“ stdafx.h”文件。它应该存在吗?)之后,我将向您提供我所拥有的东西:
Sales.h:
#pragma once
#ifndef DEPTS
#define DEPTS 2
#endif
#ifndef STORES
#define STORES 2
#endif
#ifndef MONTHS
#define MONTHS 12
#endif
using namespace std;
double storeMonthlySales[STORES][MONTHS][DEPTS] = {
{
{1.1, 1.2}, {1.3, 1.4}, {1.5, 1.6}, {1.7, 1.8}, {1.9, 2.0}, {2.1, 2.2},
{2.1, 2.2}, {2.3, 2.4}, {2.5, 2.6}, {2.7, 2.8}, {2.9, 3.0}, {3.1, 3.2}
},
{
{3.1, 3.2}, {3.3, 3.4}, {3.5, 3.6}, {3.7, 3.8}, {3.9, 4.0}, {4.1, 4.2},
{2.1, 2.2}, {2.3, 2.4}, {2.5, 2.6}, {2.7, 2.8}, {2.9, 3.0}, {3.1, 3.2}
}
};
void printMonthlySales(double ss[DEPTS][MONTHS][STORES], int mon);
Sales.cpp:
#include "Sales.h"
#include <iostream>
using namespace std;
void printMonthlySales(double ss[DEPTS][MONTHS][STORES], int mon)
{
if ((mon < 1) || (mon > MONTHS))
{
cout << "\nMonth must be a number (1 = January, through 12 = December). Try again. \n" << endl;
}
else
{
double store_total = 0;
double dept_total = 0;
double total = 0;
cout << "\t\t";
for (int h = 0; h < DEPTS; h++)
{
cout << "Department " << h + 1 << "\t\t";
}
cout << "Store Total" << endl;
for (int i = 0; i < STORES; i++)
{
cout << "Store " << i << "\t\t";
for (int j = 0; j < DEPTS; j++)
{
double d = ss[j][mon][i];
cout << d << "\t\t";
store_total += d;
total += d;
}
cout << endl;
}
cout << "Department Total\t";
for (int i = 0; i < DEPTS; i++)
{
for (int j = 0; j < STORES; j++)
{
double d = ss[j][mon][i];
cout << d << "\t\t";
}
}
cout << total << "\t\t" << endl;
}
}
这是我到目前为止对main.cpp的了解。目前还没有完成,但我只是确保自己走在正确的轨道上:
main.cpp:
#include "Sales.h"
#include <algorithm>
#include <iostream>
#include <sstream>
using namespace std;
int main(void)
{
printMonthlySales(storeMonthlySales, 1);
string a;
cin >> a;
return 0;
}
因此,到目前为止,我应该为第1个月(1月)的storeMonhtlySales打印MonthlySales。刚好有“字符串a”和“ cin >> a”来防止终端窗口自动关闭(再次,我在Visual Studio中这样做)。
但是,我正在编译它们,但出现两个错误:
LNK2005 "double (* storeMonthlySales)[12][2]" (?storeMonthlySales@@3PAY1M@1NA) already defined in main.obj
LNK1169 one or more multiply defined symbols found
我对他们为什么说printMonthlySales已经“定义”感到困惑,因为我在这里没有发现任何问题。浏览Sales.obj和main.obj文件无济于事。
答案 0 :(得分:2)
包含文件时,文件将被有效复制并粘贴到包含文件中。头文件中的所有内容现在都属于要编译的文件的一部分。#pragma once
,其他形式的包含保护可防止文件在translation unit中被多次包含。
但是...
翻译单元是单独编译的,因此它们之间没有连续性。 B.cpp无法知道A.cpp已包含给定的标头。实际上,请考虑一下,如果一个大项目中只有一个文件可以#include <string>
,那将是多么糟糕的事情。 C ++甚至在离开办公室进入贝尔实验室的走廊之前都会被浪费时间。
所以... A.cpp和B.cpp都包含header.h。它们都在header.h中拥有自己的所有内容副本。两者都可以很好地编译,但是链接器不知道如何处理竞争的定义。
在sales.h:
extern double storeMonthlySales[STORES][MONTHS][DEPTS];
extern
是一个承诺,将在storeMonthlySales
的某处定义,以便编译器可以继续进行工作。如果未定义,则链接器将抱怨。
在Sales.cpp中:
double storeMonthlySales[STORES][MONTHS][DEPTS] = {
{
{1.1, 1.2}, {1.3, 1.4}, {1.5, 1.6}, {1.7, 1.8}, {1.9, 2.0}, {2.1, 2.2},
{2.1, 2.2}, {2.3, 2.4}, {2.5, 2.6}, {2.7, 2.8}, {2.9, 3.0}, {3.1, 3.2}
},
{
{3.1, 3.2}, {3.3, 3.4}, {3.5, 3.6}, {3.7, 3.8}, {3.9, 4.0}, {4.1, 4.2},
{2.1, 2.2}, {2.3, 2.4}, {2.5, 2.6}, {2.7, 2.8}, {2.9, 3.0}, {3.1, 3.2}
}
};
这是定义。它仅存在于Sales.cpp中。包含Sales.h
的任何文件均可使用顺便提一下using namespace std;
。这会给您带来麻烦。
答案 1 :(得分:1)
由于您将storeMonthlySales
的定义放在Sales.h中,因此每当包含Sales.h时它都会重新定义。在您的情况下,这种情况发生了两次-一次出现在Sales.cpp中,一次出现在main.cpp中。一个常见的误解是#pragma once
(和标头保护符)将阻止这种情况,但事实并非如此。它们可以防止多次包括关联的.cpp文件,但不能保护.h本身。因此,解决方案是将storeMonthlySales
定义移至Sales.cpp。