0

I'm studying C on my own in preparation for my upcoming semester of school and was wondering what I was doing wrong with my code so far.

If Things look weird it is because this is part of a much bigger grab bag of sorting functions I'm creating to get a sense of how to sort numbers,letters,arrays,and the like! I'm basically having some troubles with the manipulation of strings in C currently.

Also, I'm quite limited in my knowledge of C at the moment!

My main Consists of this:

#include <stdio.h>
#include <stdio.h>                                                           
#include <stdlib.h>                                                          
int numbers[10];                                                             
int size;                                                                    
int main(void){                                                              
    setvbuf(stdout,NULL,_IONBF,0); //This is magical code that allows me to input.

    int wordNumber;                                                          
    int lengthOfWord = 50;                                                   

    printf("How many words do you want to enter: ");                         
    scanf("%i", &wordNumber);                                                
    printf("%i\n",wordNumber);                                               

    char words[wordNumber][lengthOfWord];                                    
    printf("Enter %i words:",wordNumber);                                    
    int i;                                                                   

      for(i=0;i<wordNumber+1;i++){ //+1 is because my words[0] is blank.     
            fgets(&words[i], 50, stdin);                                     
      }                                                                      

      for(i=1;i<wordNumber+1;i++){ // Same as the above comment!             
            printf("%s", words[i]); //prints my words out!                   
      }                                                                      
    alphabetize(words,wordNumber); //I want to sort these arrays with this function.
}

My sorting "method" I am trying to construct is below! This function is seriously flawed, but I'd thought I'd keep it all to show you where my mind was headed when writing this.

void alphabetize(char a[][],int size){ // This wont fly.
            size = size+1;
            int wordNumber;
            int lengthOfWord;
            char sortedWords[wordNumber][lengthOfWord]; //In effort for the for loop
            int i;
            int j;

            for(i=1;i<size;i++){ //My effort to copy over this array for manipulation
                    for(j=1;j<size;j++){
                            sortedWords[i][j] = a[i][j];
                    }
            }
            //This should be kinda what I want when ordering words alphabetically, right?
            for(i=1;i<size;i++){
                    for(j=2;j<size;j++){
                    if(strcmp(sortedWords[i],sortedWords[j]) > 0){
                            char* temp = sortedWords[i];
                            sortedWords[i] = sortedWords[j];
                            sortedWords[j] = temp;
                    }
            }
            }
            for(i=1;i<size;i++){
                    printf("%s, ",sortedWords[i]);
            }
    }

I guess I also have another question as well... When I use fgets() it's doing this thing where I get a null word for the first spot of the array. I have had other issues recently trying to scanf() char[] in certain ways specifically spacing my input word variables which "magically" gets rid of the first null space before the character. An example of this is using scanf() to write "Hello" and getting " Hello" or " ""Hello"...

Appreciate any thoughts on this, I've got all summer to study up so this doesn't need to be answered with haste! Also, thank you stack overflow as a whole for being so helpful in the past. This may be my first post, but I have been a frequent visitor for the past couple of years and it's been one of the best places for helpful advice/tips.

nishantjr
  • 1,677
  • 1
  • 14
  • 38
Genesis
  • 149
  • 12

3 Answers3

0

Function declaration and definition

The function declaration is invalid, as you've found out. You must specify the size of every dimension of the array except the first, so you might write:

void alphabetize(char a[][SOMESIZE], int size)

However, you have a non-constant second dimension (so you're using a VLA or variable length array), which means that you need to pass both sizes to the function, and pass them before you pass the array:

void alphabetize(int size, int length, char a[size][length])

and then invoke it:

alphabetize(wordNumber, lengthOfWords, words);

Of course, you should also declare the function before you try calling it.

There are probably other issues to be addressed, but this is the immediate one that jumps out. For example, you need to use size and length to control the loops in the function. You probably don't need to copy the data into the local array (in which case you don't need the local array). Etc.

You should consider compiling with options such as:

gcc -O3 -g -std=c11 -Wall -Wextra -Wmissing-prototypes -Wstrict-prototypes \
    -Wold-style-definition -Wold-style-declaration -Werror …

Note that note all versions of GCC support all those options, but use as many as are supported.

Input issue

You have:

int i;                                                                   

for (i = 0; i < wordNumber + 1; i++) { //+1 is because my words[0] is blank.     
    fgets(&words[i], 50, stdin);                                     
}

You're stepping out of bounds of your array, which potentially wreaks havoc on your code. The first entry is blank because scanf() leaves the newline in the input buffer. You should read to the end of line before going to line-based input:

int c;
while ((c = getchar()) != EOF && c != '\n')
    ;

You should also check the fgets() returns a non-null pointer; don't continue if it does.

Jonathan Leffler
  • 666,971
  • 126
  • 813
  • 1,185
  • Took me a bit get this working with my original code this morning but I got it going! Thank you very much for the explanations! Looping using the size and length to work around the words really escaped me at the time! – Genesis May 29 '14 at 20:26
0

You're going to like this - it's a derivation of QSort, adapted to your situation. It may not work quite perfectly for you without a touchup here or there (TEST FIRST!):

void qsort (Strings[], NumberOfItems)
{
   char Temp[51];    // Assumes your max string length of 50
   int I1 = 0;       // Primary index
   int I2 = 0;       // Index + 1
   int NumberOfItems_1 = 0;
   bool Swapped = false;
   do // Outer loop
   {
      Swapped = false;
      // Decrement our limit
      NumberOfItems--;

      // Save time not performing this subtraction many times
      NumberOfItems_1 = NumberOfItems - 1;

      // Repeatedly scan the list
      for (I1 = 0; I1 < NumberOfItems_1; I1++)
      {
         // Save time not performing this addition many times
         // I1 points to the current string
         // This points to the next string
         I2 = I1 + 1;

         // If the current string is greater than the next string in the list,
         // swap the two strings
         if (strcmp(Strings[I1], Strings[I2]) > 0)
         {
            strcpy (Temp, Strings[I1]);
            strcpy (Strings[I1], Strings[I2]);
            strcpy (Strings[I2], Temp);
            Swapped = true;
         }
      }
   }
   while (Swapped);     // Break out when we've got nothing left to swap
}
TDHofstetter
  • 253
  • 2
  • 7
  • I was trying to do this kind of thing from the get go and kept getting farther away from it. In order for me to do this I'd have to take my finished words and throw it all in a separate array and then stash it in this qsort right? – Genesis May 29 '14 at 03:41
  • Your existing array should be fine, but you may need to toy a bit with the arguments to the qsort function. It's wicked late here right now, and I'm too groggy to tweak it for you right now. With luck, by morning someone will have stepped in to show you the tweaks it needs. – TDHofstetter May 29 '14 at 04:28
  • You're right though, I really like this approach. Cool piece of code, thanks for sharing! – Genesis May 29 '14 at 20:27
0

I see a few things wrong with your code off the bat. First, you declare sortedWords as a multidimensional array (since you have sortedWords[wordnumber][lengthofword], but you try to use it with only one index later on.. this doesn't work! Also, your passing of the 2D array is not valid. Check out this post to see the valid ways to pass a 2D array: Passing a 2D array to a C++ function

Community
  • 1
  • 1
Shoikana
  • 585
  • 4
  • 8
  • I got away with it in the main so I was questioning what I could get away with in the function. It dawns on me now I should have gotten rid of it, but it was part of my thought process to where I was fiddling with it at the time. – Genesis May 29 '14 at 03:25