Convert a spanish string to uppercase - c

I want to convert a Spanish string to uppercase. I use the function toupper for all characters. The function does not convert characters with accent:
PROTECCIóN
Nor the enye character:
DAñO
I use the setlocale function.
setlocale(LC_ALL, "es_ES");

It is possible to get the good result with setlocale(LC_ALL, "es_ES.utf8");, and use of wchar_t and of towupper(.) function.
Output
protección daño PROTECCIÓN DAÑO
#include <stdio.h>
#include <stdlib.h>
#include <wctype.h>
#include <wchar.h>
#include <locale.h>
int main(void) {
if (!setlocale(LC_ALL, "es_ES.utf8")) return 1;
wchar_t input[] = L"protección daño";
int length = sizeof(input)/sizeof(input[0]);
wchar_t output[length];
for (int i = 0; i < length-1; ++i) {
output[i] = towupper(input[i]);
}
output[length-1] = '\0';
printf ("%ls %ls\n", input, output);
return 0;
}

Related

How do I convert a string to uppercase using the standard library?

I am trying to use a for loop with ASCII table to make every character in the string uppercase one by one by subtracting the letter number with 32. but I cant use the int i in the char str and str2. how can I do this?
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#define STRLEN 200
void string_lower() {
}
void string_upper(char str) {
char str2;
int length = strlen(str);
for (int i = 0; i < length; i++) {
str2[i] = str[i - 32];
}
}
int main() {
char word[STRLEN] = { 0 };
char word1 = 97;
printf("Write a word");
fgets(word, STRLEN, stdin);
string_upper(word);
return 0;
}
You can use toupper() to uppercase one character at a time. This will work for single byte character sets such as ASCII, but not for the UTF-8 encoding in general use today for non English scripts.
Here is a modified version:
#include <ctype.h>
#include <stdio.h>
#define STRLEN 200
char *string_upper(char *str) {
for (size_t i = 0; str[i] != '\0'; i++) {
str[i] = toupper((unsigned char)str[i]);
}
return str;
}
int main() {
char word[STRLEN];
printf("Enter a word: ");
if (fgets(word, STRLEN, stdin)) {
printf("%s", string_upper(word);
}
return 0;
}
The argument must be cast as (unsigned char)str[i] because str[i] has type char and tolower() like all functions and macros from <ctype.h> is only defined for values of the type unsigned char and the special negative value EOF. As char may be signed on some platforms, passing it directly to tolower() would have undefined behavior for negative values such as 'é' and 'ÿ'.
If you just want to make a function to convert your String to upper, maybe you can refer to the below example.
#include <stdio.h>
#include <ctype.h>
#define STRLEN 200
void string2upper(char *str){
int cursor=0;
while(*(str+cursor)!='\0'){
*(str+cursor) = toupper(*(str+cursor));
cursor++;
}
}
void main() {
char String1[STRLEN];
printf("Write a word:\n");
fgets(String1, STRLEN, stdin);
printf("Before : %s\n", String1);
string2upper(String1);
printf("After : %s\n", String1);
}
For the toupper() function, I think you can refer to this Link.
That has a detailed explanation and simple example to understand.
I think to know the function detail is better than only using~

Null When Passing String

I got this output "Hospital (null) ΓÇô Report for COVIC19 ΓÇô Community Visit"
I'm trying to printout the name of the hospital from the function readHospital() but all I got for the output is these weird looking text. So sorry I'm very new to coding.
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <conio.h>
char readHospital();
void intro(char a);
int main() {
char hospital_name;
hospital_name = readHospital();
intro(hospital_name);
}
char readHospital() {
char a[100];
printf("Enter Hospital Name: ");
fgets(a, 100, stdin);
return a;
}
void intro(char hospital_name) {
printf("Hospital %s – Report for COVIC19 – Community Visit", hospital_name);
}
I've changed your code, The readHospital function that you are using in your code is not a correct function for reading the input string from the user and returning it.
Instead, you can use the readNewString function that I've written.
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <conio.h>
char * readNewString();
void intro(char a[100]);
int main() {
char * hospital_name;
hospital_name = readNewString();
intro(hospital_name);
}
char *readNewString(void) {
char buffer[1024];
if (!fgets(buffer, sizeof buffer, stdin)) {
return NULL; // read failed, e.g., EOF
}
int len = strlen(buffer);
if (len > 0 && buffer[len - 1] == '\n') {
buffer[--len] = '\0'; // remove the newline
// You may also wish to remove trailing and/or leading whitespace
} else {
// Invalid input
//
// Depending on the context you may wish to e.g.,
// consume input until newline/EOF or abort.
}
char *str = malloc(len + 1);
if (!str) {
return NULL; // out of memory (unlikely)
}
return strcpy(str, buffer); // or use `memcpy` but then be careful with length
}
void intro(char hospital_name[100]) {
printf("Hospital %s – Report for COVIC19 – Community Visit", hospital_name);
}
Please note that hospital_name is of char type and you return a string, char list char*

inserting comma in a large int number

i am trying to insert a comma in a large integer number eg, 870120000 and present it as: 870,120 and the last three digits are discarded. The format will allways be the same, ie., xxxxxxxxx number where i am only interested in the first 6 digits.
What i have been doing so fare is using snprintf:
#include <stdio.h>
#include <string.h>
int main()
{
char buffer[5];
unsigned int lNum= 870120000;
int cx;
memset(buffer,0,sizeof(buffer));
cx = snprintf(buffer, 4, "%d,", lNum);
buffer[3] = ',';
printf("%s\n",buffer);
cx = snprintf(buffer+4, 4, "321"); // Note 1 ???
printf("%s\n", buffer);
return 0;
}
My problem is that i am stuck at (comment // Note 1), how do I add the last next three digits in to buffer ?
in addition I would like to know if this approch is ideal or is there any better(easier) way to do this?
You can do that in two steps. First convert the lNum into a string, then cut the needed parts out of this string. Something like that.
#include <stdio.h>
#include <stdlib.h>
int main(void) {
char tmp[256], out[256];
unsigned int lNum= 870120000;
sprintf(tmp, "%u", lNum);
sprintf(out, "%3.3s,%3.3s", tmp, tmp+3);
printf("%s\n", out); // prints 870,120
return 0;
}
See http://ideone.com/bnQNou
Or you can convert it into a float and change the locale to have "," as delimiter:
#include <stdio.h>
#include <locale.h>
int main()
{
unsigned int lNum = 870120000;
setlocale(LC_NUMERIC, "de_DE");
printf("%3.3f\n", (float)(870120000 / 1000000)); // prints 870,120
return 0;
}
First of all to hold 870,120 you have to define a 8 chars buffer.
So you can use %f format specifier to do what you the job, e.g.:
#include <stdio.h>
#include <string.h>
int main()
{
char buffer[8] = {0};
unsigned int lNum= 870120000;
snprintf(buffer, sizeof(buffer), "%3.3f", (float)(lNum)/(1000000));
char *temp = strstr(buffer, ".");
if (temp != NULL)
{
*temp = ',';
}
printf("%s\n",buffer);
return 0;
}
or another example using double snprintf and a given number of integer part digits and decimal part digits.
#include <stdio.h>
#include <string.h>
#include <stdint.h>
#define INT_DIGIT 3
#define DEC_DIGIT 3
int main()
{
char temp_buffer[128];
char buffer[INT_DIGIT+DEC_DIGIT+2] = {0};
unsigned int lNum= 87012000;
snprintf(temp_buffer, sizeof(temp_buffer), "%u",lNum);
snprintf(buffer, sizeof(buffer), "%.*s,%.*s", INT_DIGIT, temp_buffer, DEC_DIGIT, &temp_buffer[INT_DIGIT]);
printf("%s\n",buffer);
return 0;
}

segfault reading wide-oriented stream with locale settings

I have problem in program with locale and reading from stdin with fgetws function.
#include <stdio.h>
#include <locale.h>
#include <wchar.h>
static const int N = 2;
int main(void) {
setlocale(LC_ALL, "");
wchar_t data[N];
fgetws(data, N, stdin);
printf("%ls\n", data);
/* fclose(stdin); */
return 0;
}
When input is long enough (5 or more chars) I get segfault if I don't close stdin before return. Why is that? What is wrong with this program?
Suspect fgetws(data, 2, stdin) is broken.
fgetws(), using such a small buffer should, at most, read 1 wchar_t from stdin and append a termanting (wchar_t) '\0'.
As usual, when code fails mysteriously, best to check return from the functions to see if they are as expected.
#include <stdio.h>
#include <locale.h>
#include <wchar.h>
#include <assert.h>
#include <stdio.h>
#include <locale.h>
#include <wchar.h>
static const int N = 2;
int main(void) {
char *p = setlocale(LC_ALL, "");
assert(p);
wchar_t data[N];
wchar_t *s = fgetws(data, N, stdin);
assert(s);
int i = printf("%ls\n", data);
assert(i == 2);
i = fclose(stdin);
assert(i == 0);
return 0;
}

Iterate through char array and print chars

I am trying to print each char in a variable.
I can print the ANSI char number by changing to this printf("Value: %d\n", d[i]); but am failing to actually print the string character itself.
What I am doing wrong here?
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main(int argc, char *argv[])
{
int len = strlen(argv[1]);
char *d = malloc (strlen(argv[1])+1);
strcpy(d,argv[1]);
int i;
for(i=0;i<len;i++){
printf("Value: %s\n", (char)d[i]);
}
return 0;
}
You should use %c format to print characters in C. You are using %s, which requires to use pointer to the string, but in your case you are providing integer instead of pointer.
The below will work. You pass in the pointer to a string when using the token %s in printf.
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main(int argc, char *argv[])
{
int len = strlen(argv[1]);
char *d = malloc (strlen(argv[1])+1);
strcpy(d,argv[1]);
printf("Value: %s\n", d);
return 0;
}

Resources