Thread: setting variables to command line arguments

  1. #1
    Registered User
    Join Date
    Dec 2005
    Location
    german border
    Posts
    72

    setting variables to command line arguments

    Hi,

    I am trying to make my program alter the number of times it requests info by using command line arguments. However I can't assign a variable to the value of the argument in the array i.e. int var = argv[2];

    Code:
    #include<iostream>
    #include<string>
    #include<cmath>
    #include <iomanip>
    
    using namespace std;
    
    void transferTime ( int hddSpeeds[], float sizeOfDir, float transferRate[] );
    
    int main(int argc, char *argv[])
    {
    	char control = argv[2];
    	string hddNames[control];
    	float transferRate[control];
    	int hddSpeeds[control];
    	float sizeOfDir;
    	float counter = 0;
    	int fastest;
    	for ( int loop = 0; loop < control; loop++ )
    	{//open loop
    		cout<<"Please enter a harddrive name to be compared: ";
    		cin>> hddNames[loop];
    		cout<<"Please enter the transfer speed of that drive in megabits per second: ";
    		cin>> hddSpeeds[loop];
    	}//end loop
    	cout<<"Please enter the size of the directory being transferred in Gigabytes: ";
    	cin>> sizeOfDir;
    	transferTime( hddSpeeds, sizeOfDir, transferRate, control );
    	for ( int loop = 0; loop < control; loop++ )
    	{//open loop
    		if ( counter < transferRate[loop] )
    		{//open if
    			 fastest = loop;
    		}//close if
    	}//close loop
    	float topspeed;
    	topspeed = transferRate[fastest];
    	cout<<"Hard Drive\tTransfer rate (Mbps)\tDirectory Size(GB)\tTransfer time(s)\n";
    	for (int loop = 0; loop < control; loop++ )
    	{//open loop
    		cout<< hddNames[loop] << "\t\t";
    		cout<< hddSpeeds[loop] << "\t\t\t";
    		cout<< sizeOfDir << "\t\t\t";
    		cout<< std::fixed << setprecision(1) << topspeed << "\n";
    	}//close loop
    	cout<<"\n";
    	cout<<"The fastest of the given Hard Drives was: \n";
    	cout<<"Hard Drive\tTransfer rate (Mbps)\tDirectory Size(Gb)\tTransfer time(s)\n";
    	cout<< hddNames[fastest] << "\t\t";
    	cout<< hddSpeeds[fastest] << "\t\t\t"; 
    	cout<< sizeOfDir << "\t\t\t"; 
    	cout<< std::fixed << setprecision(1) << topspeed << "\n";
    }
    
    void transferTime ( int hddSpeeds[], float sizeOfDir, float transferRate[], int control )
    {
    	for (int loop = 0; loop < control; loop++ )
    	{//open loop
    		int dummy = hddSpeeds[loop];
    		transferRate[loop] = sizeOfDir * 1024 * 8/dummy;
    	}//close loop
    	return;
    }
    Here are the errors I am getting:

    Code:
    hdd.cpp: In function ‘int main(int, char**)’:
    hdd.cpp:12: error: invalid conversion from ‘char*’ to ‘char’
    hdd.cpp:8: error: too many arguments to function ‘void transferTime(int*, float, float*)’
    hdd.cpp:28: error: at this point in file
    Thanks in advance.

  2. #2
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,660
    Because all args are strings, so even if you do

    myprog 123

    You end up with "123"
    So perhaps
    myint = atoi( argv[2] );

    Also, you should check argc before looking at argv

    > string hddNames[control];
    Variable length arrays are not standard C++
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  3. #3
    Registered User
    Join Date
    Nov 2003
    Posts
    161
    Also to add at the very beginning
    void transferTime ( int hddSpeeds[], float sizeOfDir, float transferRate[] );

    does not match the function at the bottom.

    for var = argv ....
    a sollution is:
    create a char* and use strcpy to copy it to the pointer. (obviously properly allocated)

  4. #4
    Registered User
    Join Date
    Dec 2005
    Location
    german border
    Posts
    72
    Thanks for the replies. Sorry I am very new to c++ so could you maybe give me an example of how to do the strcat method please?

    Also so if I can't use variable length arrays how do I solve my problem? or does it still work but just isn't official?

  5. #5
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    You are using the C++ string class, so don't use strcpy or strcat. It's not necessary here anyway, since the point is that you need an int version of the command line argument.

    For the variable length arrays, it is allowed on some compilers because it is legal in C. In C++ you would generally use a vector instead of arrays for this (another option is dynamic arrays with new[]/delete[]). Whether you switch to the other alternatives or not is up to you, and it depends on whether this code is only for a one-time project like a homework assignment, or if you are trying to write code that will work in other places.

    Another solution if you really aren't supposed to be using vectors or dynamic arrays is to use a maximum size and make the arrays that size, then only use part of the arrays based on the control value.

  6. #6
    Registered User
    Join Date
    Dec 2005
    Location
    german border
    Posts
    72
    ok I understand what you are saying. This is just for practice but I would like to learn to code properly, so I will definetly look into vector arrays. However I would like to try to get it working with dynamic arrays first, if not I'll just use vector arrays.

    I have updated the code and now it will compile but I get a segmentation fault.

    Code:
    #include<iostream>
    #include<string>
    #include<cmath>
    #include <iomanip>
    
    using namespace std;
    
    void transferTime ( int hddSpeeds[], float sizeOfDir, float transferRate[], int control );
    
    int main(int argc, char *argv[])
    {	
    	int control;
    	control = atoi( argv[2] );
    	string hddNames[control];
    	float transferRate[control];
    	int hddSpeeds[control];
    	float sizeOfDir;
    	float counter = 0;
    	int fastest;
    	for ( int loop = 0; loop < control; loop++ )
    	{//open loop
    		cout<<"Please enter a harddrive name to be compared: ";
    		cin>> hddNames[loop];
    		cout<<"Please enter the transfer speed of that drive in megabits per second: ";
    		cin>> hddSpeeds[loop];
    	}//end loop
    	cout<<"Please enter the size of the directory being transferred in Gigabytes: ";
    	cin>> sizeOfDir;
    	transferTime( hddSpeeds, sizeOfDir, transferRate, control );
    	for ( int loop = 0; loop < control; loop++ )
    	{//open loop
    		if ( counter < transferRate[loop] )
    		{//open if
    			 fastest = loop;
    		}//close if
    	}//close loop
    	float topspeed;
    	topspeed = transferRate[fastest];
    	cout<<"Hard Drive\tTransfer rate (Mbps)\tDirectory Size(GB)\tTransfer time(s)\n";
    	for (int loop = 0; loop < control; loop++ )
    	{//open loop
    		cout<< hddNames[loop] << "\t\t";
    		cout<< hddSpeeds[loop] << "\t\t\t";
    		cout<< sizeOfDir << "\t\t\t";
    		cout<< std::fixed << setprecision(1) << topspeed << "\n";
    	}//close loop
    	cout<<"\n";
    	cout<<"The fastest of the given Hard Drives was: \n";
    	cout<<"Hard Drive\tTransfer rate (Mbps)\tDirectory Size(Gb)\tTransfer time(s)\n";
    	cout<< hddNames[fastest] << "\t\t";
    	cout<< hddSpeeds[fastest] << "\t\t\t"; 
    	cout<< sizeOfDir << "\t\t\t"; 
    	cout<< std::fixed << setprecision(1) << topspeed << "\n";
    }
    
    void transferTime ( int hddSpeeds[], float sizeOfDir, float transferRate[], int control )
    {
    	for (int loop = 0; loop < control; loop++ )
    	{//open loop
    		int dummy = hddSpeeds[loop];
    		transferRate[loop] = sizeOfDir * 1024 * 8/dummy;
    	}//close loop
    	return;
    }
    here is the error, this is received when I try to execute.

    Code:
    Segmentation fault (core dumped)

  7. #7
    Hurry Slowly vart's Avatar
    Join Date
    Oct 2006
    Location
    Rishon LeZion, Israel
    Posts
    6,788
    check argc value before accessing argv[2]
    check control value before using it
    All problems in computer science can be solved by another level of indirection,
    except for the problem of too many layers of indirection.
    – David J. Wheeler

  8. #8
    Registered User
    Join Date
    Dec 2005
    Location
    german border
    Posts
    72
    Sorry I don't understand what you mean by check? Print them out?

  9. #9
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    Make sure they exist and are valid. You can do this by printing them out or using a debugger.

    Also, you could mention what command line arguments you are giving your program. It will most likely crash on anything where the second argument does not exist or is non-numeric.

  10. #10
    Registered User
    Join Date
    Nov 2005
    Posts
    85
    something like:
    Code:
    if(argc!=2) {
       cout << "Wrong arguments specified\n";
       exit(0);
    }

  11. #11
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    argc has to be greater than or equal to 3 for argv[2] to be valid.
    Last edited by Daved; 11-01-2006 at 11:57 PM. Reason: correction from vart

  12. #12
    Hurry Slowly vart's Avatar
    Join Date
    Oct 2006
    Location
    Rishon LeZion, Israel
    Posts
    6,788
    not less than...
    Code:
    int control = 0;
    if (argc >= 3)
       control = atoi(argv[2]);
    
    if (control >= 0)
    {
       //do your stuff
    }
    All problems in computer science can be solved by another level of indirection,
    except for the problem of too many layers of indirection.
    – David J. Wheeler

  13. #13
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    True.

    Also, I think you'd want control to be greater than (and not equal to) 0 if you are using it to size your arrays.

  14. #14
    Hurry Slowly vart's Avatar
    Join Date
    Oct 2006
    Location
    Rishon LeZion, Israel
    Posts
    6,788
    true - my fault. Probably was still half sleeping
    All problems in computer science can be solved by another level of indirection,
    except for the problem of too many layers of indirection.
    – David J. Wheeler

  15. #15
    Registered User
    Join Date
    Dec 2005
    Location
    german border
    Posts
    72
    Thanks guys, I got it working. However, I have to do the following './speedcalc2 - 5' I must include the '-' to make argc to 3 is there no way around this? or can I make c++ use '-5' instead?

    Thanks in advance.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 10
    Last Post: 09-27-2005, 12:49 PM
  2. Setting OS Environment Variables
    By ImNotMad in forum C Programming
    Replies: 4
    Last Post: 10-23-2003, 02:07 AM
  3. ASP help. Setting variables within an <a> tag
    By TravisS in forum Tech Board
    Replies: 6
    Last Post: 03-28-2003, 04:56 AM
  4. Your favourite fantasy game setting?
    By fry in forum Game Programming
    Replies: 4
    Last Post: 10-16-2002, 06:26 AM
  5. Having trouble correctly setting DJGPP's env. variables in XP
    By Unregistered in forum C Programming
    Replies: 0
    Last Post: 06-05-2002, 10:51 PM