0

I'm trying to complete an assignment. What is meant by the term "modifying in-place without creating a copy" and "return value is the same value that was passed into the function"?

How do I check if my code satisfies both condition?

// converts all lowercase into uppercase

char* mystrupr(char *string)
{
    int myStrlen = strlen(string);
    for (int i = 0; i < myStrlen; i++)
        if (string[i] >= 'a' && string[i] <= 'z')
            *(string + i) -= 32;

    return string;
}

I'm assuming that I had violated the conditions as when I was using this function in another part of my program, it gave me the errors:

passing argument 1 of 'mystrupr' discards 'const' qualifier from pointer target type [-Werror=discarded-qualifiers]
note: expected 'char *' but argument is of type 'const char *'

said code fragment that uses the uppercase function:

int spellcheck(char const *word) {
.
.
mystrupr(word);
.
.
}

*edit (making a copy)

int spellcheck(char const *word) {
.
.
char *myWord = word
mystrupr(myWord);
.
.
}
xiaozaiz
  • 69
  • 1
  • 6
  • 3
    Yes, your mystrupr does modify the string without making a copy and returns the same argument it's called with, so that looks good to me. – Rup Sep 13 '20 at 10:35
  • 2
    The problem in spellcheck is that its argument is a `const char*` and so should not be modified, but you're then passing this into mystrupr to be modified. So you'll need to work out whether the argument that spellcheck is given can be modified or not, and if it can't you'll need to make a copy of the string there before passing it to mystrupr. – Rup Sep 13 '20 at 10:37
  • thanks for the replies, by making a copy, do you mean what is shared above (under *edit), if so, its still giving me the error "initialization discards 'const' qualifier from pointer target type" – xiaozaiz Sep 13 '20 at 10:43
  • `char *myWord = word;` - that's not enough to make a copy, no, that's just copying the pointer (and casting away the `const`) and not copying the string that the pointer is pointing to. The easiest way is to use [strdup()](https://en.cppreference.com/w/c/experimental/dynamic/strdup), then free() the copy when you're done with it. (However [some people don't like strdup()](https://stackoverflow.com/questions/12984948/why-is-strdup-considered-to-be-evil), but I think it's OK to use.) – Rup Sep 13 '20 at 10:44
  • ahh i understand now, thanks so much for your help – xiaozaiz Sep 13 '20 at 10:48

3 Answers3

1

To "modify in place" in this context means that the function changes the data referenced by its parameter. If you pass a string in the form of a char *, then the caller's copy of the string is modified. An alternative way of processing the string would be to return a modified copy of the string, while leaving the original unchanged. If the function does not change the original, and it's designed that way, it's helpful to define the parameter as const. This is both more expressive, because it's clear that the data is not modified, and it allows the compiler to spot careless errors that might, in fact, modify the data.

If a function "returns the same value" it means exactly that -- that the return is exactly the argument. In principle, there's no reason that a function should ever return the value of a specific argument, since the caller always knows what the value is -- otherwise it wouldn't have been able to supply it to the function in the first place. However, many long-standing functions (e.g., strcpy) do, in fact, return one of their arguments.

Kevin Boone
  • 4,092
  • 1
  • 11
  • 15
-1

Modifying a string in-place without creating a copy:

First, since the function changes the input string in-place, it does not need to return anything.

Second, since the function changes the input string in-place, it cannot take a constant string as input.

For example, you can do this:

char str[] = "abc"; // constant string contents are copied into the array at declaration
mystrupr(str);

But you cannot do this:

char* str = "abc"; // constant string address is copied into the variable at declaration
mystrupr(str);

Here is how you can implement this function:

void mystrupr(char* string)
{
    for (int i = 0; string[i] != 0; i++)
        if (string[i] >= 'a' && string[i] <= 'z')
            string[i] = string[i] - 'a' + 'A';
}
goodvibration
  • 5,980
  • 4
  • 28
  • 61
-1

When you declare function parameter as const and you try to modify using tricks and hacks - it is an Undefined Behaviour and that program is wrong.

When you need to modify something never declare it contst and never pass the const data to it. In your case compiler is warning about it.

0___________
  • 60,014
  • 4
  • 34
  • 74