Functions fopen/calloc/malloc and and ways of their replacement - c

I want to make a simple program (but difficult for me), which will find contacts by letters (parts of the name are entered using numbers) and by numbers (parts of the number). Input - numbers, from the standard input (txt file), output - contacts that contain these numbers (letters). The contact file looks like
(name)
(number)
(name)
(…)
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <string.h>
#define MAX_NAME (128)
#define MAX_NUM (32)
/*
IN :
contacts.txt :
Sad Mirrow
38074025
Deniel Kovalski
78032596
Miky Trance
88055535
Martin Worried
77432651
96 [key number from standard entry]
OUT:
Deniel Kovalski
[because 96 matches in his number]
Martin Worried
[96 matches in his name Wo]
*/
typedef struct Contact {
char* name;
char* number;
} Contact;
char matchTable[10][9] = {
"0+", "1", "2abcABC", "3defDEF", "4ghiGHI",
"5jklJKL", "6mnoMNO", "7pqrsPQRS", "8tuvTUV", "9wxyWXY"
};
bool find(char c, char key){
int j = key - '0';
for (int i = 0; matchTable[j][i] != '\0'; i++){
if (c == matchTable[j][i])
return true;
}
return false;
}
bool matches(char* src, char* key){
unsigned int i,j;
for (i = 0; src[i] != '\0'; i++){
int tmp = i;
for (j = 0; key[j] != '\0'; j++){
if (find(src[tmp], key[j]))
tmp++;
else
break;
}
if (j == strlen(key))
return true;
}
return false;
}
int main(){
char key[MAX_NUM];
scanf("%s", key);
size_t arrSize = 32;
Contact* contacts = malloc(arrSize * sizeof(Contact));
int k = 0;
size_t nameSize = MAX_NAME;
size_t numSize = MAX_NUM;
char *nameBuf = malloc(MAX_NAME);
char *numBuf = malloc(MAX_NUM);
FILE* f = fopen("contacts.txt", "r");
while (fgets(nameBuf, nameSize, f)
&& fgets(numBuf, numSize, f)){
contacts[k].name = malloc(MAX_NAME);
contacts[k].number = malloc(MAX_NUM);
strcpy(contacts[k].name, nameBuf);
strcpy(contacts[k].number, numBuf);
k++;
if (k == arrSize);
arrSize <<= 1;
contacts = realloc(contacts, arrSize * sizeof(Contact));
}
for (int i = 0; i < k; i++){
bool matchesName = matches(contacts[i].name, key);
bool matchesNumber = matches(contacts[i].number, key);
if (matchesName || matchesNumber)
printf("%s\n", contacts[i].name);
}
for (int i = 0; i < k; i++){
free(contacts[i].name);
free(contacts[i].number);
}
free(contacts);
free(nameBuf);
free(numBuf);
fclose(f);
return 0;
}
At first we did as we could. Then was a time to fulfill the conditions of the task and the problem came. It needs to be done without malloc/calloc/fopen. I tried to fix everything, but I ran into a problem that the program does not work and it seems to me that I'm confused.
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <string.h>
#define MAX_NAME (128)
#define MAX_NUM (64)
struct Folio
{
char name[1000];
char num[1000];
};
static char matchTable[10][9] = {
"0+", "1", "2abcABC", "3defDEF", "4ghiGHI",
"5jklJKL", "6mnoMNO", "7pqrsPQRS", "8tuvTUV", "9wxyWXY"
};
int find(char c, char key){
int j = key - '0';
for (int i = 0; matchTable[j][i] != '\0'; i++){
if (c == matchTable[j][i])
return 1;
}
return 0;
}
int matches(char* src, char* key){
unsigned int i,j;
for (i = 0; src[i] != '\0'; i++){
unsigned int tmp = i;
for (j = 0; key[j] != '\0'; j++){
if (find(src[tmp], key[j]))
tmp++;
else
break;
}
if (j == strlen(key))
return 1;
}
return 0;
}
int main(){
char key[MAX_NUM];
scanf("%s", key);
struct Folio contacts[42]; //Entry entries[42]
int contacts_count = 0; //entries_count = 0;
//FILE* f = fopen("seznam.txt", "r");
char name[1000];
char num[1000]; //number[1000]
while (fgets(name, MAX_NAME, stdin) != NULL && fgets(num, MAX_NUM, stdin) != NULL)
{
// copy to struct
strcpy(contacts[contacts_count].name, name);
strcpy(contacts[contacts_count].num, num);
contacts_count++;
}
for (int i = 0; i < contacts_count; i++){
int matchesName = matches(contacts[contacts_count].name, key);
int matchesNumber = matches(contacts[contacts_count].num, key);
if (matchesName || matchesNumber)
printf("%s%s\n", contacts[contacts_count].name, contacts[contacts_count].num);
}
//fclose(f);
return 0;
}
I want to ask the help of experienced programmers.

matchTable[10][9] is too small to save "7pqrsPQRS" as a string as needed in matchTable[j][i] != '\0';. Needs 10.
Suggest
//static char matchTable[10][9] = {
// "0+", "1", "2abcABC", "3defDEF", "4ghiGHI",
// "5jklJKL", "6mnoMNO", "7pqrsPQRS", "8tuvTUV", "9wxyWXY"
//};
static char *matchTable[10] = {
"0+", "1", "2abcABC", "3defDEF", "4ghiGHI",
"5jklJKL", "6mnoMNO", "7pqrsPQRS", "8tuvTUV", "9wxyWXY"
};
Perhaps other issues too.

I believe the main issue is the the search logic. Code loops over all contacts, but will attempt a match against the a non-existing contacts entry.
for (int i = 0; i < contacts_count; i++){
int matchesName = matches(contacts[contacts_count].name, key);
int matchesNumber = matches(contacts[contacts_count].num, key);
...
Should this use the i-th contacts ?
for (int i = 0; i < contacts_count; i++){
int matchesName = matches(contacts[i].name, key);
int matchesNumber = matches(contacts[i].num, key);
if (matchesName || matchesNumber)
printf("%s%s\n", contacts[i].name, contacts[contacts_count].num);
}
Or even
for (int i = 0; i < contacts_count; i++){
struct Folio con_p = &contacts[i] ;
int matchesName = matches(con_p->name, key);
int matchesNumber = matches(con_p->num, key);
if (matchesName || matchesNumber)
printf("%s%s\n", con_p->name, con_p->num);
}
Also take a look at answer from chux - Reinstate Monica

Related

strcmp returns __strcmp_sse2_unaligned () in a simple string search programme

I am currently fighting with a primitive search routine. It uses strcmp to compare a string given against a two dim array of strings.
GDP returns:
"__strcmp_sse2_unaligned () at ../sysdeps/x86_64/multiarch/strcmp-sse2-unaligned.S:30 30 ../sysdeps/x86_64/multiarch/strcmp-sse2-unaligned.S: No such file or directory".
Edited: Trying to move on, added command line for string input procedure. Somehow, it is mistaken.
here is my code
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
char dictionary()
{
char **strings = (char**)malloc(5*sizeof(char*));
int i = 0;
for(i = 0; i < 5; i++){
//printf("%d\n", i);
strings[i] = (char*)malloc(7*sizeof(char));
}
sprintf(strings[0], "mark");
sprintf(strings[1], "ala");
sprintf(strings[2], "wojtek");
sprintf(strings[3], "tom");
sprintf(strings[4], "john");
for(i = 0; i < 5; i++){
printf("Line #%d(length: %lu): %s\n", i, strlen(strings[i]),strings[i]);
}
for(i = 0; i < 5; i++){
free(strings[i]);
}
free(strings);
}
int cmp(char *s1, char *s2[][10]){
int i = 0;
//size_t l = strlen(s1);
for (i = 0; i < 5; i++){
if (strcmp(s1, s2[i][7*sizeof(char)]) == 0)
{
printf("OK \n");
} else {
printf("sth is wrong \n");
}
return 0;
}
}
int main(){
char BufText[255];
int n=0;
char sign;
fflush(stdin);
n = 0;
do {
sign = getchar();
BufText[n ++] = sign;
if(n >= 253) break;
} while (sign !='\n');
BufText [n] = 0;
char **dict = dictionary();
cmp(BufText, dict);
free_dictionary(dict);
return 0;
}
As said in the comments, there's a lot of flaws in your code.
First in your main, you're trying to cmp("ala", dictionary); but dictionary is an undeclared variable. I think you wanted to use the result of your dictionary() call into the cmp call. So you need to store the dictionary() result into your dictionary variable. It can't actually be done because your dictionary() func does not return anything and free the allocated dict before it can be used.
I could continue this way but here's a patched version of your code. Feel free to ask for clarifications.
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
char **dictionary()
{
char **dict = (char**)malloc(sizeof(char*) * 5);
int i = 0;
for (i = 0; i < 5; i++)
dict[i] = (char*)malloc(sizeof(char) * 7);
sprintf(dict[0], "mark");
sprintf(dict[1], "ala");
sprintf(dict[2], "wojtek");
sprintf(dict[3], "tom");
sprintf(dict[4], "john");
for (i = 0; i < 5; i++)
printf("Line #%d(length: %lu): %s\n", i, strlen(dict[i]),dict[i]);
return (dict);
}
void free_dictionary(char **dict)
{
for (int i = 0; i < 5; i++)
free(dict[i]);
free(dict);
}
void cmp(char *s1, char *s2[5])
{
int i = 0;
for (i = 0; i < 5; i++)
{
if (strcmp(s1, s2[i]) == 0)
printf("OK \n");
else
printf("sth is wrong \n");
}
}
int main()
{
char **dict = dictionary();
cmp("ala", dict);
free_dictionary(dict);
return (0);
}

C rename() can't seem to get it to work

I'm trying to make a program that takes in a database of listfile names and compare it with another list. When there is a match it should rename the file with that name to the corresponding relationNumber.
At the end of the code I try to rename the file, but it doesn't let me. Is it because I'm trying to pass chars instead of const chars? And if so, how can I solve this? Before I try to rename the file I printed the strings out to see what is in them and the strings contain; "Zaalstra legitimatie.txt" and "1.17234842.txt" which is what I want. Thanks in advance.
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define relationLen 10
#define true 1
#define false 0
#define resetptr NULL
typedef int bool;
char* strcasestr(char* haystack, char* needle) {
size_t i, j;
if (!needle[0])
return (char*) haystack;
for (i = 0; haystack[i]; i++) {
bool matches = true;
for (j = 0; needle[j]; j++) {
if (!haystack[i + j])
return NULL;
if (tolower((unsigned char)needle[j]) != tolower((unsigned char)haystack[i + j])) {
matches = false;
break;
}
}
if (matches)
return (char *)(haystack + i);
}
return NULL;
}
int main(void) {
char database[1024][30];
char name[30] = {0};
char newName[30] = {0};
char extension[1024][5];
char lined[256], linef[256];
char relationNumber[] = "1.1";
char newRelationNumber[relationLen] = {0};
char *ret, *number;
int i, j, c, k, len = 0;
FILE* filef = fopen("filelist.txt", "r");
for(i = 0; (c = fgetc(filef)) != EOF; i++) {
fgets(linef, sizeof(linef), filef);
strcpy(database[i], (char[2]){(char) c, '\0'});
strcat(database[i], linef);
len = strlen(database[i]);
for(j = 0, k = 5; j < 4; j++, k--) {
extension[i][j] = database[i][len-k];
}
printf("%s ", extension[i]);
printf("%s", database[i]);
}
FILE* filed = fopen("Database.txt", "r");
fgets(lined, sizeof(lined), filed);
printf("%s", lined);
number = strstr(lined, relationNumber);
for(i = 0; lined[i] != 9; i++)
newName[i] = lined[i];
newName[i] = '\0';
for(i = 0; i < relationLen; i++)
newRelationNumber[i] = number[i];
newRelationNumber[i] = '\0';
number = resetptr;
strcat(newRelationNumber, ".txt");
ret = strcasestr(database[i], newName);
printf("%s", database[0]);
printf("%s", newRelationNumber);
i = rename(database[0], newRelationNumber);
printf("\n%d", i);
return 0;
}

Creating list of ip addresses over a specific range in C

I am writing a tool to scan all the nodes on a network but I have ran in to a problem. I'm writing the tool in C but I'm new to the language so I'm not sure how the iterate through the address range.
The user will give the argument 192.168.*.* and it will create every IP address in that range, e.g. 192.168.1.1, 192.168.1.2, 192.168.1.3 and then eventually 192.168.2.1, 192.168.2.2, 192.168.2.3 etc.
My previous code was:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void scanner(int s)
{
char addr[20];
for (int i = 0; i < 255; ++i)
{
sprintf(addr, "192.168.%d.%d", s, i);
printf("%s\n", addr);
}
}
int main()
{
for (int i = 0; i < 255; ++i)
{
scanner(i);
}
return 0;
}
But I don't know how to run this from the user input.
You can take the inputs from the user using the scanf function. I have updated your code to use the same -
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int addr_byte_0;
int addr_byte_1;
void scanner(int s)
{
char addr[200];
int i;
for (i = 0; i < 255; ++i)
{
sprintf(addr, "%d.%d.%d.%d", addr_byte_0, addr_byte_1, s, i);
printf("%s\n", addr);
}
}
int main()
{
int i;
//printf("Enter the first byte of the address: ");
scanf ("%d", &addr_byte_0);
//printf("Enter the second byte of the address: ");
scanf ("%d", &addr_byte_1);
for (i = 0; i < 255; ++i)
{
scanner(i);
}
return 0;
}
Also, as per C standards you cannot declare a variable inside the for loop. Hence I have moved the declaration out of the for loop. Hope this helps!
Inspired by (e.g. python-) generators, my solution doesn't perform dynamic memory allocation and and has constant memory consumption. I don't like that I currently rely on a do while loop. Also the explicit check for ig->num_wildcards == 0 is ugly. Anyways:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define IP_OCTETS 4
#define MAX_UCHAR 255
typedef struct {
int wildcard_pos[IP_OCTETS];
int num_wildcards;
int counter[IP_OCTETS];
int octet[IP_OCTETS];
} ip_generator;
char* mystrsep(char** stringp, const char* delim)
{
char* start = *stringp;
char* p;
p = (start != NULL) ? strpbrk(start, delim) : NULL;
if (p == NULL)
{
*stringp = NULL;
}
else
{
*p = '\0';
*stringp = p + 1;
}
return start;
}
void init_ip_gen(ip_generator *ig, char* ip_mask)
{
char *token, *string;
char* ip_mask_ptr = ip_mask;
const char delimiters[] = ".";
int i = 0;
while ((token = mystrsep(&ip_mask_ptr, delimiters)) != NULL)
{
ig->wildcard_pos[i] = -1;
if (strcmp(token, "*") == 0)
{
ig->wildcard_pos[ig->num_wildcards] = i;
ig->counter[ig->num_wildcards] = 1;
ig->num_wildcards++;
}
else
{
ig->octet[i] = atoi(token);
}
i++;
}
}
int ig_next(ip_generator *ig)
{
int i;
int carry = 1;
if (ig->num_wildcards == 0)
{
return 0;
}
for (i = ig->num_wildcards - 1; i >= 0; i--)
{
if (carry == 1)
{
if (ig->counter[i] == MAX_UCHAR)
{
ig->counter[i] = 1;
}
else
{
ig->counter[i]++;
carry = 0;
}
}
if (carry == 0)
{
break;
}
if (i == 0 && carry == 1)
{
return 0;
}
}
return 1;
}
void generate_ip(ip_generator *ig, char *ip)
{
int i;
int j = 0;
int oct[IP_OCTETS];
for (i = 0; i < IP_OCTETS; i++)
{
if (i == ig->wildcard_pos[j])
{
oct[i] = ig->counter[j];
j++;
}
else
{
oct[i] = ig->octet[i];
}
}
sprintf(ip, "%d.%d.%d.%d", oct[0], oct[1], oct[2], oct[3]);
}
int main()
{
char ip_mask[] = "192.*.10.*";
//char ip_mask[] = "192.1.10.123";
ip_generator ig;
memset(&ig, 0, sizeof(ig));
init_ip_gen(&ig, ip_mask);
char ip[32];
memset(ip, 0, sizeof(ip));
do
{
generate_ip(&ig, ip);
printf("%s\n", ip);
} while (ig_next(&ig));
return 0;
}

Caesar Cipher not returning correct key

So my decrypter program seems to not be able to find the key and implement it by itself. I noticed that if I changed the key to equal -5 which is the correct key it would print out the decrypted text correctly. However I am unable to figure out how to make the program figure it out by itself without having me to put it in manually. Any help would be greatly appreciated! Thank you!
rotUtils.h
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include "rotUtils.h"
int rotate(int c, int n){
if (n == 0) return c;
int nRot = abs(n) % (RANGECHAR + 1);
if(n > 0)
return rotatePlus(c + nRot);
else
return rotateMinus(c - nRot);
}
int rotatePlus(int sum){
int diff = sum - MAXCHAR;
if (sum > MAXCHAR) sum = MINCHAR + diff - 1;
return sum;
}
int rotateMinus(int sum){
int diff = MINCHAR - sum;
if (sum < MINCHAR) sum = MAXCHAR - diff + 1;
return sum;
}
decrypt.cpp
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include "rotUtils.h"
bool solved( char decodearr[], char dictarr[][30], int size1, int size2){
char* compared;
bool result = false;
for(int j = 0; j < size2; j++){
compared = strstr( decodearr, dictarr[j]);
}
if( compared != '\0'){
result = true;
}
return result;
}
int decode( char codearr[], char dictarr[][30], int size1, int size2)
{
bool solution = false;
int key = -50; This is where I had to change it to -5 to solve
char decodearr[10000];
while(solution == false && key < 51)
{
for( int i = 0; i < size1; i++)
{
if(!isspace(codearr[i]))
{
decodearr[i] = rotate(codearr[i], key);
}
else
decodearr[i] = codearr[i];
}
solution = solved( decodearr, dictarr, size1, size2);
if( solution == false)
{
key++;
}
}
for( int j = 0; j < size1; j++)
{
codearr[j] = decodearr[j];
}
return key;
}
int main( int argc, char* argv[])
{
char* file = argv[1];
char* dictionary = argv[2];
char code[10000];
char dict[30000][30];
FILE* codeFile;
codeFile = fopen(file, "r");
int i = 0;
int j = 0;
int key;
FILE* dictFile;
dictFile = fopen(dictionary, "r");
while(!feof(codeFile))
{
code[i] = fgetc(codeFile);
i++;
}
code[ i ]= '\0';
fclose(codeFile);
while(!feof(dictFile))
{
fscanf(dictFile, "%s", dict[j]);
j++;
}
key = decode(code, dict, i, j);
fclose(dictFile);
for(int k = 0; k < i; k++)
{
printf("%c", code[k]);
}
printf( "\nThe key is: %d\n", key);
return 0;
}
Solved() will only return true if there is a match on the last dictionary word currently, you have to move that check inside. You could print to screen whenever you find a key that has a match on your dictionary and/or keep a list of possible keys then print after you are done with them all, right now you would exit as soon as you find any match even if it was just luck.

Count the number of occurrences of each letter in string

How can I count the number of occurrences in c of each letter (ignoring case) in the string? So that it would print out letter: # number of occurences, I have code to count the occurences of one letter, but how can I count the occurence of each letter in the string?
{
char
int count = 0;
int i;
//int length = strlen(string);
for (i = 0; i < 20; i++)
{
if (string[i] == ch)
{
count++;
}
}
return count;
}
output:
a : 1
b : 0
c : 2
etc...
Let's assume you have a system where char is eight bit and all the characters you're trying to count are encoded using a non-negative number. In this case, you can write:
const char *str = "The quick brown fox jumped over the lazy dog.";
int counts[256] = { 0 };
int i;
size_t len = strlen(str);
for (i = 0; i < len; i++) {
counts[(int)(str[i])]++;
}
for (i = 0; i < 256; i++) {
if ( count[i] != 0) {
printf("The %c. character has %d occurrences.\n", i, counts[i]);
}
}
Note that this will count all the characters in the string. If you are 100% absolutely positively sure that your string will have only letters (no numbers, no whitespace, no punctuation) inside, then 1. asking for "case insensitiveness" starts to make sense, 2. you can reduce the number of entries to the number of characters in the English alphabet (namely 26) and you can write something like this:
#include <ctype.h>
#include <string.h>
#include <stdlib.h>
const char *str = "TheQuickBrownFoxJumpedOverTheLazyDog";
int counts[26] = { 0 };
int i;
size_t len = strlen(str);
for (i = 0; i < len; i++) {
// Just in order that we don't shout ourselves in the foot
char c = str[i];
if (!isalpha(c)) continue;
counts[(int)(tolower(c) - 'a')]++;
}
for (i = 0; i < 26; i++) {
printf("'%c' has %2d occurrences.\n", i + 'a', counts[i]);
}
Like this:
int counts[26];
memset(counts, 0, sizeof(counts));
char *p = string;
while (*p) {
counts[tolower(*p++) - 'a']++;
}
This code assumes that the string is null-terminated, and that it contains only characters a through z or A through Z, inclusive.
To understand how this works, recall that after conversion tolower each letter has a code between a and z, and that the codes are consecutive. As the result, tolower(*p) - 'a' evaluates to a number from 0 to 25, inclusive, representing the letter's sequential number in the alphabet.
This code combines ++ and *p to shorten the program.
One simple possibility would be to make an array of 26 ints, each is a count for a letter a-z:
int alphacount[26] = {0}; //[0] = 'a', [1] = 'b', etc
Then loop through the string and increment the count for each letter:
for(int i = 0; i<strlen(mystring); i++) //for the whole length of the string
if(isalpha(mystring[i]))
alphacount[tolower(mystring[i])-'a']++; //make the letter lower case (if it's not)
//then use it as an offset into the array
//and increment
It's a simple idea that works for A-Z, a-z. If you want to separate by capitals you just need to make the count 52 instead and subtract the correct ASCII offset
#include <stdio.h>
#include <string.h>
void main()
{
printf("PLEASE ENTER A STRING\n");
printf("GIVE ONLY ONE SPACE BETWEEN WORDS\n");
printf("PRESS ENETR WHEN FINISHED\n");
char str[100];
int arr[26]={0};
char ch;
int i;
gets(str);
int n=strlen(str);
for(i=0;i<n;i++)
{
ch=tolower(str[i]);
if(ch>=97 && ch<=122)
{
arr[ch-97]++;
}
}
for(i=97;i<=122;i++)
printf("%c OCCURS %d NUMBER OF TIMES\n",i,arr[i-97]);
return 0;
}
After Accept Answer
A method that meets these specs: (IMO, the other answers do not meet all)
It is practical/efficient when char has a wide range. Example: CHAR_BIT is 16 or 32, so no use of bool Used[1 << CHAR_BIT];
Works for very long strings (use size_t rather than int).
Does not rely on ASCII. ( Use Upper[] )
Defined behavior when a char < 0. is...() functions are defined for EOF and unsigned char
static const char Upper[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
static const char Lower[] = "abcdefghijklmnopqrstuvwxyz";
void LetterOccurrences(size_t *Count, const char *s) {
memset(Count, 0, sizeof *Count * 26);
while (*s) {
unsigned char ch = *s;
if (isalpha(ch)) {
const char *caseset = Upper;
char *p = strchr(caseset, ch);
if (p == NULL) {
caseset = Lower;
p = strchr(caseset, ch);
}
if (p != NULL) {
Count[p - caseset]++;
}
}
}
}
// sample usage
char *s = foo();
size_t Count[26];
LetterOccurrences(Count, s);
for (int i=0; i<26; i++)
printf("%c : %zu\n", Upper[i], Count[i]);
}
You can use the following code.
main()
{
int i = 0,j=0,count[26]={0};
char ch = 97;
char string[100]="Hello how are you buddy ?";
for (i = 0; i < 100; i++)
{
for(j=0;j<26;j++)
{
if (tolower(string[i]) == (ch+j))
{
count[j]++;
}
}
}
for(j=0;j<26;j++)
{
printf("\n%c -> %d",97+j,count[j]);
}
}
Hope this helps.
#include<stdio.h>
#include<string.h>
#define filename "somefile.txt"
int main()
{
FILE *fp;
int count[26] = {0}, i, c;
char ch;
char alpha[27] = "abcdefghijklmnopqrstuwxyz";
fp = fopen(filename,"r");
if(fp == NULL)
printf("file not found\n");
while( (ch = fgetc(fp)) != EOF) {
c = 0;
while(alpha[c] != '\0') {
if(alpha[c] == ch) {
count[c]++;
}
c++;
}
}
for(i = 0; i<26;i++) {
printf("character %c occured %d number of times\n",alpha[i], count[i]);
}
return 0;
}
for (int i=0;i<word.length();i++){
int counter=0;
for (int j=0;j<word.length();j++){
if(word.charAt(i)==word.charAt(j))
counter++;
}// inner for
JOptionPane.showMessageDialog( null,word.charAt(i)+" found "+ counter +" times");
}// outer for
#include<stdio.h>
void frequency_counter(char* str)
{
int count[256] = {0}; //partial initialization
int i;
for(i=0;str[i];i++)
count[str[i]]++;
for(i=0;str[i];i++) {
if(count[str[i]]) {
printf("%c %d \n",str[i],count[str[i]]);
count[str[i]]=0;
}
}
}
void main()
{
char str[] = "The quick brown fox jumped over the lazy dog.";
frequency_counter(str);
}
Here is the C code with User Defined Function:
/* C Program to count the frequency of characters in a given String */
#include <stdio.h>
#include <string.h>
const char letters[] = "abcdefghijklmnopqrstuvwxzy";
void find_frequency(const char *string, int *count);
int main() {
char string[100];
int count[26] = { 0 };
int i;
printf("Input a string: ");
if (!fgets(string, sizeof string, stdin))
return 1;
find_frequency(string, count);
printf("Character Counts\n");
for (i = 0; i < 26; i++) {
printf("%c\t%d\n", letters[i], count[i]);
}
return 0;
}
void find_frequency(const char *string, int *count) {
int i;
for (i = 0; string[i] != '\0'; i++) {
p = strchr(letters, string[i]);
if (p != NULL) {
count[p - letters]++;
}
}
}
Have checked that many of the answered are with static array, what if suppose I have special character in the string and want a solution with dynamic concept. There can be many other possible solutions, it is one of them.
here is the solutions with the Linked List.
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
struct Node {
char data;
int counter;
struct Node* next;
};
void printLinkList(struct Node* head)
{
while (head != NULL) {
printf("\n%c occur %d", head->data, head->counter);
head = head->next;
}
}
int main(void) {
char *str = "!count all the occurances of character in string!";
int i = 0;
char tempChar;
struct Node* head = NULL;
struct Node* node = NULL;
struct Node* first = NULL;
for(i = 0; i < strlen(str); i++)
{
tempChar = str[i];
head = first;
if(head == NULL)
{
node = (struct Node*)malloc(sizeof(struct Node));
node->data = tempChar;
node->counter = 1;
node->next = NULL;
if(first == NULL)
{
first = node;
}
}
else
{
while (head->next != NULL) {
if(head->data == tempChar)
{
head->counter = head->counter + 1;
break;
}
head = head->next;
}
if(head->next == NULL)
{
if(head->data == tempChar)
{
head->counter = head->counter + 1;
}
else
{
node = (struct Node*)malloc(sizeof(struct Node));
node->data = tempChar;
node->counter = 1;
node->next = NULL;
head->next = node;
}
}
}
}
printLinkList(first);
return 0;
}
int charset[256] = {0};
int charcount[256] = {0};
for (i = 0; i < 20; i++)
{
for(int c = 0; c < 256; c++)
{
if(string[i] == charset[c])
{
charcount[c]++;
}
}
}
charcount will store the occurence of any character in the string.
//This is JavaScript Code.
function countWordOccurences()
{
// You can use array of words or a sentence split with space.
var sentence = "The quick brown fox jumped over the lazy dog.";
//var sentenceArray = ['asdf', 'asdf', 'sfd', 'qwr', 'qwr'];
var sentenceArray = sentence.split(' ', 1000);
var output;
var temp;
for(var i = 0; i < sentenceArray.length; i++) {
var k = 1;
for(var j = i + 1; j < sentenceArray.length; j++) {
if(sentenceArray[i] == sentenceArray[j])
k = k + 1;
}
if(k > 1) {
i = i + 1;
output = output + ',' + k + ',' + k;
}
else
output = output + ',' + k;
}
alert(sentenceArray + '\n' + output.slice(10).split(',', 500));
}
You can see it live --> http://jsfiddle.net/rammipr/ahq8nxpf/
//c code for count the occurence of each character in a string.
void main()
{
int i,j; int c[26],count=0; char a[]="shahid";
clrscr();
for(i=0;i<26;i++)
{
count=0;
for(j=0;j<strlen(a);j++)
{
if(a[j]==97+i)
{
count++;
}
}
c[i]=count;
}
for(i=0;i<26;i++)
{
j=97+i;
if(c[i]!=0) { printf("%c of %d times\n",j,c[i]);
}
}
getch();
}
protected void btnSave_Click(object sender, EventArgs e)
{
var FullName = "stackoverflow"
char[] charArray = FullName.ToLower().ToCharArray();
Dictionary<char, int> counter = new Dictionary<char, int>();
int tempVar = 0;
foreach (var item in charArray)
{
if (counter.TryGetValue(item, out tempVar))
{
counter[item] += 1;
}
else
{
counter.Add(item, 1);
}
}
//var numberofchars = "";
foreach (KeyValuePair<char, int> item in counter)
{
if (counter.Count > 0)
{
//Label1.Text=split(item.
}
Response.Write(item.Value + " " + item.Key + "<br />");
// Label1.Text=item.Value + " " + item.Key + "<br />";
spnDisplay.InnerText= item.Value + " " + item.Key + "<br />";
}
}

Resources