I had recieved an email sometime ago wherein I was asked to write a function that parsed a given string for the longest pallindrome it contained and replaced the pallindrome with another string, given as its second argument. In finding a pallindrome, however, all the characters were to be considered equal. Therefore, a space, a comma, or any punctuation for that matter was to be treated like any other character.

In solving that question, here's what I came up with after a try or two:

Code:
//File R.h
#ifndef __R__
#define __R__
#include<stdio.h>
#include<stdlib.h>
#include<string.h>

#define MAX_LEN 1000

int ReplacePallindromes(char**, char*);
int Replace(char**, const int, const int, const
char*);
char* SubString(char*, const int, const int);
void Reverse(char*);

enum MatchTypes
{
None=0,
OddLength=1,
EvenLength=2
};

#endif



//File Globals.h
#include "R.h"

int ReplacePallindromes(char **InStr, char
*ReplaceWith)
{

int Len, LenReplaceWith, MatchFound, LastReplacement;

int Counter;
int ReverseCounter;
int SomeCounter;
int SomeOtherCounter;

char* SubStr1;
char* SubStr2;

LastReplacement=-100;
SubStr1=SubStr2=NULL;
MatchFound=0;

if (*InStr==NULL || ReplaceWith==NULL) return -1;
if (*ReplaceWith==0) return -1;
LenReplaceWith=strlen(ReplaceWith);
Len=strlen(*InStr);
if (Len<2) return -1;

Counter=ReverseCounter=SomeCounter=SomeOtherCounter=0;

for(Counter=0; Counter<Len; Counter++)
{


NextCharFromFront:
	for(ReverseCounter=Len-1; ReverseCounter>Counter; ReverseCounter--)
	{
		if (*((*InStr)+Counter) == *((*InStr)+ReverseCounter))
		{
			MatchFound=1;
			for(SomeCounter=1, SomeOtherCounter=ReverseCounter-1; 
			Counter+SomeCounter<=SomeOtherCounter; SomeCounter++, SomeOtherCounter--)
			{
				SubStr1=SubString(*InStr, Counter, Counter+SomeCounter);

				SubStr2=SubString(*InStr, SomeOtherCounter, ReverseCounter);
				Reverse(SubStr2);

				MatchFound=((strcmp(SubStr1, SubStr2)==0)? 1:0);
				if (MatchFound==0)
				{
					free(SubStr1);
					free(SubStr2);
					break;
				}
				
				free(SubStr1);
				free(SubStr2);
			}//End of SomeCounter for loop

			if(MatchFound==1 && Counter+SomeCounter>=SomeOtherCounter)
			{
				//This is the largest pallindrome, replace it
				LastReplacement=Replace(InStr, Counter, ReverseCounter, ReplaceWith);
				Len=strlen(*InStr);
				Counter=LastReplacement+1;
				goto NextCharFromFront;
			}
		}//End of if InStr[Counter] == InStr[ReverseCounter]
	}//End of ReverseCounter for loop
}// End of Counter for loop


return 0;

} //end of function



int Replace(char **InStr, const int From, 
const int To, const char *ReplaceWith)
{

char* NewString;
int LenReplaceWith, Counter, k, Len;

if(*InStr==NULL || ReplaceWith==NULL) return -1;
Len=strlen(*InStr);
LenReplaceWith=strlen(ReplaceWith);


NewString=NULL;

NewString=(char*)malloc(sizeof(char)*(Len-(To-From+1)+LenReplaceWith+1));
for(Counter=0;
Counter<(Len-(To-From+1)+LenReplaceWith+1); Counter++)
*(NewString+Counter)=0;

for(Counter=0;Counter<=From-1;Counter++)
*(NewString+Counter)=*((*InStr)+Counter);

for(Counter=0;Counter<LenReplaceWith; Counter++)
 *(NewString+From+Counter)=*(ReplaceWith+Counter);

for(Counter=To+1, k=0; Counter<Len; Counter++, k++)
	*(NewString+From+LenReplaceWith+k)=*((*InStr)+Counter);

*(NewString+From+LenReplaceWith+k)=0;

free(*InStr);
Len=strlen(NewString);
*InStr=(char*)malloc(sizeof(char)*(Len+1));
if((*InStr)==NULL) return -1;
strcpy(*InStr, NewString);
free(NewString);

return (From-1+LenReplaceWith);

}


char* SubString(char* Source, const int From, const
To)
{

int Len, Counter;
char *NewString;
Len=strlen(Source);
if(Source==NULL) return NULL;
if (From<0) return NULL;
if (From>To) return NULL;
if ((From>Len) || (To>Len)) return NULL;
NewString=(char*)malloc(sizeof(char)*(To-From+2));
for(Counter=From; Counter<=To; Counter++)
{
*(NewString+Counter-From)=*(Source+Counter);
}
NewString[Counter-From]=0;
return NewString;
}

void Reverse(char* Str)
{
int i, j, len;
char temp;
i=j=len=temp=0;

if(Str!=NULL)
{
len=strlen(Str);
for (i=0, j=len-1; i<=j; i++, j--)
{
temp=Str[i];
Str[i]=Str[j];
Str[j]=temp;
}
}
}


//File R.C
//R.C
#include "R.h"

int main(void)
{

char c, *InStr, *ReplaceWith;
int i;


c=' ';
i=0;

InStr=(char*)malloc(sizeof(char)*(MAX_LEN+1));
if(InStr==NULL) return -1;
ReplaceWith=(char*)malloc(sizeof(char)*(MAX_LEN+1));
if(ReplaceWith==NULL) return -1;

printf("\nEnter a string (1000 characters maximum):");
while(((c=getchar())!=EOF) && (c!='\n') & (i<=MAX_LEN)) InStr[i++]=c;
InStr[i]=0;

c=' ';
i=0;
printf("\n\nEnter the string that you wish to replace\npallindromes with (1000 characters maximum): ");
while(((c=getchar())!=EOF) && (c!='\n') & (i<=MAX_LEN)) ReplaceWith[i++]=c;
ReplaceWith[i]=0;


	if(ReplacePallindromes(&InStr, ReplaceWith)==0)
	{
		printf("\nThe modified string is:\n\n %s\n", InStr);
	}
	else
	{
		printf("An error occured. The program will now end.");
		free(InStr);
		free(ReplaceWith);
		return -1;
	}

	free(InStr);
	free(ReplaceWith);
	return 0;
}
I was asked as to why I'd taken a pointer to a pointer as the first argument of the ReplacePallindrome function. I thought I'd write a tutorial to explain this thing that I'd arrived at by heuristic endeavours in the past, when I practiced pointers. So here's a tutorial I've written. I present it to all of you learned people out here, so you may review it, because, with a few refinements, I intend to get it published if it is all ok. I am only learning C and thus have written only what I've coded and tested with my own hands. Please give me your comments as to how good or bad it is.

Thanks!