Оригинальный код в вашем посте использует дополнительный (ненужный) слой косвенности для kcalTopp
, что приводит к попыткам манипулировать массивом адресов (указателей), а не манипулировать значениями int
, указанными в памяти. Это, в свою очередь, может быть причиной того, что вы видите ошибки сегментации, возникающие при попытке доступа к памяти, которой вы не владеете. Для некоторых входных значений и в зависимости от того, в какой день вы запускаете вашу программу, она может запускаться и может иметь sh.
(иногда это называется неопределенным поведением и является причиной что проблема не всегда проявляется, заставляя вас думать, что ваша программа безупречна, если это не так.)
Следующее содержит изменения в вашем исходном коде с целью иллюстрации некоторых предложений в комментарии . (не исправлять каждую ошибку logi c.) Редактирование включает обработку kcalTopp
в качестве указателя на int
память, а не на массив int *
. Смотрите пояснения в комментариях:
//void sort(int *kcalTopp[], int numTopps);//*kcalTopp[] is an array of pointers
void sort(int *kcalTopp, int numTopps);//*kcalTopp is a pointer to 'int' memory
int main(int argc, char *argv[])
{
int numTopps, doughPrice, eachToppPrice, kcalDough, i, j, totalKcal, highest, kcalperDol;
//scanf("%d %d %d %d", &numTopps, &doughPrice, &eachToppPrice, &kcalDough);
if(argv != 5) //simple reading in of command line args
{
printf("4 input values required. Exiting");
return 0;
}
//note, each of these calls includes simple for test for success before going on
numTopps = strtol(argv[1], (char **) NULL, 10);
if(errno == ERANGE) {printf("argv[1] Bad input, exiting"); return 0;}
doughPrice = strtol(argv[2], (char **) NULL, 10);
if(errno == ERANGE) {printf("argv[2] Bad input, exiting"); return 0;}
eachToppPrice = strtol(argv[3], (char **) NULL, 10);
if(errno == ERANGE) {printf("argv[3] Bad input, exiting"); return 0;}
kcalDough = strtol(argv[4], (char **) NULL, 10);
if(errno == ERANGE) {printf("argv[4] Bad input, exiting"); return 0;}
int *kcalTopp;
//This statement (without cast) is sufficient to create memory for kcalTopp
kcalTopp = malloc(sizeof(int)*numTopps);
if(!kcalTopp)//should always test before using memory
{
printf("memory allocation failed, exiting");
return 0;
}
for(i=0; i<numTopps; i++)
{
scanf("%d", &kcalTopp[i]);
}
totalKcal=kcalDough;
highest=totalKcal/doughPrice;
//sort(&kcalTopp, numTopps);
// ^ not needed
sort(kcalTopp, numTopps);
for(i=0; i<numTopps; i++)
{
for(j=0; j<=i; j++)
{
totalKcal=totalKcal+kcalTopp[j];
kcalperDol=totalKcal/(doughPrice+i*eachToppPrice);
if(kcalperDol>highest)
{
highest=kcalperDol;
}
}
}
printf("%d", highest);
return 0;
}
void sort(int *kcalTopp, int numTopps)//note removal of []
{
int temp, i;
for(i=0; i<(numTopps-1); i++)
{
if(kcalTopp[i]<kcalTopp[i+1])
{
temp=kcalTopp[i];//note removal of '*' from all kcalTopp
kcalTopp[i]=kcalTopp[i+1];
kcalTopp[i+1]=temp;
}
}
}