-1

I've been trying to bend my head around this problem for a week now, but I can't seem to find anything online and I've given up on trying to solve it on my own.

My assignment is to write a program which will read names from a file and accept new entries from the user, then sort the entires and write them out to the file. The only crux about this is that I have to sort them in a function and use pointers to do so. This code is supposed to be written in C++ aswell, using character arrays.

The code I have right now looks like this. This is a working version, the only problem is that I don't use neither pointers or a function to sort the names.

#include<iostream>
#include<cstdlib>
#include<fstream>
#include<cstring>

bool sorted;

using namespace std;

int main()
{
    int i = 0;
    int numNames = 0;
    ifstream ifs;
    ifs.open("namn.txt");

    char c[20][20];

    if(ifs.is_open())
    {
        while(!ifs.eof())
        {
            ifs >> c[i];
            i++;
        }
    }

    cout<<"How many names do you want to enter?"<<endl;
    cin>>numNames;

    for(int l = i-1; l<numNames+i-1; l++)
    {
        system("cls");
        cout<<"Enter a name: ";
        cin>>c[l];
    }
    while(sorted == false)
    {
        for(int j = 0; j<numNames+i-1; j++)
        {
            for(int k = j; k<numNames+i-1; k++)
            {
                if(c[j][0] > c[k][0])
                {
                    char snorre[20];
                    strcpy(snorre,c[j]);
                    strcpy(c[j],c[k]);
                    strcpy(c[k],snorre);
                }
                else if(c[j][0] == c[k][0])
                {
                    if(c[j][1] > c[k][1])
                    {
                        char snorre[20];
                        strcpy(snorre,c[j]);
                        strcpy(c[j],c[k]);
                        strcpy(c[k],snorre);
                    }
                }
            }
        }
        cout<<endl<<endl<<endl;
        ofstream ofs;
        ofs.open("namn.txt");
        for(int o = 0; o<numNames+i-1; o++)
        {
            cout<<c[o]<<" ";
            ofs<<c[o]<<endl;
        }
        ofs.close();
        system("pause");
        sorted = true;
    }
}

So hopefully someone could help me out with this problem, thanks in advance! :)

Yoldrim
  • 53
  • 7
  • http://stackoverflow.com/questions/5605125/why-is-iostreameof-inside-a-loop-condition-considered-wrong – M.M Jan 31 '17 at 13:30
  • I think your sort will not work if the strings have the first 2 characters the same (and some other cases) – M.M Jan 31 '17 at 13:31
  • probably the intended answer will be to create an array of pointers , each pointing to one string, and then sort the pointers, and not use `strcpy`. (This is absolutely terrible by modern coding standards, but it sounds like your assignment hasn't been updated since 1985) – M.M Jan 31 '17 at 13:32
  • Yes, I'm aware this is probably really horribly written, it's something I threw togheter in 5 minutes before I got the instructions, and it's just in the post to give people an idea of what the code should be like. And I know it won't work if the first two are the same, and I know how to solve that just haven't got to it :) I will definitely look into array of pointers though, that seems like the right way to go from here. Thanks a lot! – Yoldrim Jan 31 '17 at 13:36
  • For the sorting function, you could encapsulate your nested for loops inside a function which takes as parameters `c` and `numNames`. And to get the sorting work properly, you could use `strcmp` to compare the char arrays or write your own string comparing function. – Polb Jan 31 '17 at 13:44
  • The sorting function works just fine! I will make it more efficent using strcmp and such when I get finished with my current problem. – Yoldrim Jan 31 '17 at 13:54
  • @Yoldrim look at my answer below that includes both of the things you wanted. I didn't add finished code because I believe it will be better for you to solve it yourself :) – Ofer Arial Jan 31 '17 at 14:11

2 Answers2

0

To get your code to use pointers and functions, you can do this- you should change your code and make it use the following:

First, Get each name from the file to an std::string, using getline(ifstream_object, std::string_object), for reference see here.

Convert each one to a const char * (also shown in that example), using .c_str().

Do the following to each of the new names entered.

Store all names entered in this array pointers: char *names[20];, like this: names[i] = name;

Next, Create a function such as follows:

int location_of_bigger_string(const char* s1, const char* s2)
{
    // Returns 1 if s1 should be before s2 and 2 otherwise
    // This way, you use functions and pointers together.
    // Use strcmp(s1,s2) here to determine returning value
}

strcmp(char*, char*) - read about it here.

Finally, to sort all the strings, use qsort or this example.

Community
  • 1
  • 1
Ofer Arial
  • 1,129
  • 1
  • 10
  • 25
  • after using `getline` with `string`, the strings can be compared with relational operators, and sorted with `sort`. – M.M Jan 31 '17 at 13:53
  • Amazing explanation! Will try this when I get to my computer, currently on my way home hehe. – Yoldrim Jan 31 '17 at 14:55
0

Here's the complete code,

Note that the compare function gets pointers to the elements, here the elements are pointers themselves, so what's passed to "compare" function is of type "char **"

{

#include "stdafx.h"
#include<iostream>

//retruns +1 if str1 > str2 alphabetically
int compare(const void * a, const void * b )
{
    const char * str1 = *((const char **)a);
    const char * str2 = *((const char **)b);

    int i;
    for ( i = 0 ; str1[i] && str2[i] ; i++ )
    {
        if ( str1[i] > str2[i] )
        {
            return +1;
        }
        else if ( str1[i] < str2[i] )
        {
            return -1;
        }
    }

    //one or both strings have ended


    if (str1[i]) //str1 is longer
        return +1;
    else if (str2[i]) //str2 is longer
        return -1;
    else
        return 0;
}
int _tmain(int argc, _TCHAR* argv[])
{
    char * names[]={"Zebra","Kousha","Koosha","Kou","Koush","Test"};

    qsort( names, 6, sizeof(char *), compare );

    return 0;
}

}