Question Details:
I have a homework problem which I've been working on for a couple of days now but being a non-CS major, I'm having trouble finding the solution. I'm going to post the problem in great detail, followed by my current code (which doesn't work).
Problem
Two phrases are anagrams if you can rearrange the letters of one to get the other. For example, an anagram of "Dormitory" is "Dirty Room". Notice that the differences between capital and small letters are ignored when determining if one phrase is an anagram of another (as are punctuation and whitespace). Your program should ask the user to enter two phrases, and will determine whether or not the two phrases are anagrams.

Your program must include the following functions:

  1. inputPhrase This function reads in a phrase (maximum 30 characters) that is typed at the keyboard. The function returns the phrase, stored in a character array. It also returns the size of the array (the number of characters stored in the array). If the user types in more than 30 characters, only the first 30 are stored in the array.
    You should define the value 30 as a global constant using the #define directive.

Please note that you are NOT using strings in this assignment (as described in Chapter 8 - we haven't talked about them, yet), and you should NOT be using the string handling functions described in Chapter 8. In particular, the inputPhrase function should accept the user's input one character at a time (set up a loop that reads in one character with each iteration of the loop. The loop should terminate if the user types the ENTER key or if 30 characters have already been read in.)

  1. cleanUpPhrase The purpose of this function is to remove whitespace and punctuation from a phrase, and to change all alphabetic characters to lower case letters. The function reduces the size of the array as whitespace and punctuation characters are removed, and returns the new size to the calling function.

  2. countChar This function is given three inputs: a character (ch), an array of type char, and the size of the array. The function returns the number of occurrences of ch in the array. This function is called by isAnagram.

  3. isAnagram Given two character arrays, and the size of each array, the function returns 1 (true) if the two phrases stored in the arrays are anagrams of each other, and returns 0 (false) otherwise.

Sample Output

                ANAGRAM TESTER

You will be asked to input two phrases.  This program will
determine if the phrases are anagrams.

Enter your first phrase (30 characters or less)
>Douglas Hofstadter
Enter your second phrase (30 characters or less)
>god of ruthless data!

Your phrases are anagrams

My Code:

#include <stdio.h> /* provides scanf, printf, getchar */
#include <ctype.h> /* provides tolower, isalpha */

#define MAX_CHARS 30 /* defines the value of characters equal to 30 as a global
             constant */

void inputPhrase(int *n1, int *n2); /* This function reads in a phrase, maximum of 30 characters,
                       entered by the user. Function returns the phrase, stored in
                       a character array. Also returns the size of the array. Only
                       the first 30 characters are stored in the array if the array
                       size is greater than 30. */

void inputPhrase(int *n1, int *n2)
{
    char msg1[MAX_CHARS], ch1;
    char msg2[MAX_CHARS], ch2;
    int i = 0;

    printf("Enter your first phrase (30 characters or less)\n");
    while((ch1 = getchar()) != '\n')
    {
        msg1[i++] = ch1;
    }

    &n1 = i;

    i = 0;

     printf("Enter your second phrase (30 characters or less)\n");
    while((ch2 = getchar()) != '\n')
    {
        msg2[i++] = ch2;
    }

    &n2 = i;

    /* Returns the phrase entered by the user
    msg1[i] = '\0';  prevents garbage from being place at end of array
                     output

    n = i;

    i = 0;

    while(msg[i] != '\0')
    {
        printf("%c", msg[i++]);
    }
    */

    return;
}


/*
void cleanUpPhrase(char msg[i])
{
  char ch1, ch2;

}
*/

  /*
void countChar(char character, char array[], int size)
{
}

int isAnagram(char array1[], char array2[], int array1size, int array2size)
{
}
*/


int main()
{
  void inputPhrase(int *n1, int *n2);
  int n1;

  /*
  int size = inputPhrase();

    if(size >= MAX_CHARS)
      {
    size = 30;
      }
  */
    printf("\n%d\n", n1);
    return 0;
}

I know I have some unfinished stuff in there, but I'm having trouble with quite a number of things as you could easily tell by just reading my code. I've tried a bunch of other websites already and this isn't from my book. I don't know anyone in the class since I'm the only sophomore in it and the teacher isn't very helpful. I'll definetely do whatever it is you ask in order to show I'm at least trying here. Please help me out, thanks.

the functions count_char and test_letter_content are from
something else, but they provide:

an example of changing case
a way to compare the letter content of two char arrays

I put a "main()" on the code so you can see how it works.
You will have to find a way to trim char arrays.

The principle is to add up characters characters based on their ascii code - string the result in an array of integers.
Thne you compare the two arrays (in this case) only for uppercase ascii values.

#include <string.h>
#include <ctype.h>
#include <stdlib.h>
#include <stdio.h>

/* count characters, there must be at least one */
int count_chars( int *dest, char *src)
{
	int i=0;
	int retval=0;
	size_t len=strlen(src);
	
	for(i=0;i<len;i++)     /* sum occurrences of each letter */
	{	
		if(isalpha((int) src[i]) ) /* is is a letter */
		{			           
			dest[ toupper((int) src[i]) ]++;  /* count as uppercase */
			retval++;
		}	
	}	
	return retval;
}

/* compare letter content of two char arrays */
int test_letter_content(char *a, char *b)
{
	int ascii_a[128]={0};
	int ascii_b[128]={0};
	int i=0;
	int retval=0;
                                  
    if(!strlen(a) || !strlen(b) ) return retval; /* check lengths */
    retval=count_chars(ascii_a, a);       /* count letters in a */
    if(!retval) return retval;
    retval=count_chars(ascii_b, b);       /* count letters in b */
    if(!retval) return retval;
	retval=1;                             /*assume okay at this point */
	for(i='A';i<='Z' && retval==1 ;i++)
	{
		if(ascii_a[i]!=ascii_b[i]) retval=0;
	}
	return retval;
}

/* this is a test - note a & b will overflow on long entries */
int main(int argc, char *argv[])
{
	char a[32]={0x0};
	char b[32]={0x0};
	const char verb[2][8]={"are not", "are"};
	
	if(argc!=3)
	{
		fprintf(stderr,"bad parameters: requires two parms\n");	
		exit(EXIT_FAILURE);
	}
	strcpy(a,argv[1]);
	strcpy(b,argv[2]);
	printf("%s and %s ",a,b);
	printf("%s ", verb[ test_letter_content(a,b) ]);
	printf("identical letter-wise\n");
	return 0;
}

Jim, you need to have the condition as

if((ascii_a[i] == 0 && ascii_b[i] != 0) || (ascii_a[i] != 0 && ascii_b[i] == 0))

instead of

if(ascii_a[i]!=ascii_b[i])

because anagrams don't care for repeated alphabets

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.