Hello, and welcome.
In this lecture, I want to talk about a couple operators that are a little bit strange in the sense that
you wouldn't necessarily think they're operators.
Because all the operators we learned up to this point really just point to you know
sort of using the symbol to do calculations on numbers.
And these operators actually sort of look like functions.
So let's talk about the cast in the sizeof operator.
In order to first talk about the cast operator,
I have to tell you a little bit about type conversions, how data is being converted.
We learned all about data types and different data types out there.
But if you're actually trying to assign data to different types,
there's some implicit conversions that go on in the c programming language.
So conversion of data between different types can happen automatically
and this is referred to as implicit conversion
by the language or explicitly by the program by the program or.
The programmer itself the developer can do something.
They can use a cast operator essentially to do a conversion.
The data that's being converted implicitly
is really important because you have to understand this because most
c program that you're going to develop in order to effectively develop them,
you have to understand these rules for these conversions.
Because you're going to often have integers and floating point numbers,
decimal numbers and whole numbers.
And you're going to be using them intermixing them kind of sometimes.
And when you do, you have to know how things are being converted.
Now you should try to avoid that as much as you can by using the cast operator.
But when you don't use the cast operator, understand what's going on.
And what's going on here when you assign data
to different types floats and doubles,
the data is either going to be truncated or it's going to be promoted.
These are two terms that you're going to hear.
Truncated means becomes less precise
and promoted means it becomes more precise.
So try not to mix these types but they may be useful.
The main thing to understand is we know from earlier lectures that c is very flexible.
And that's a conscious decision by the designers of the language.
When they wanted to have it flexible but again as a trade-off,
as this additional freedom is given to you,
you can abuse it. And so don't abuse
this idea of mixing types.
Try to use the same types when you can, integers with integers, floats with floats.
But when you can't,
either understand the implicit conversions or
do the explicit conversions using the cast operator.
So again, another issue
or another concept where c is flexible, but you shouldn't abuse it.
So whenever a floating point value is assigned to an integer variable in c,
so you have int x, float y,
x equals y.
The decimal portion of the number is going to get truncated.
So if you have a number int x equals 0,
float f equals 12.125
and you assign f to x, the value of x is going to be 12.
You're going to lose that precision. The value's going to get truncated
because you're assigning a float to an int. An int only knows how to store a whole number.
So it's automatically getting converted by the programming language, by the compiler to 12.
Only the importation is going to be stored.
Now if you assign an integer variable to a floating point variable, which is the opposite,
it doesn't cause any change in the value of the number.
The value is converted by the system and stored in the floating variable.
So that you don't really have to worry about, assigning it into a flow.
If you assign 12 to a flow, it's still going to be 12, just 12.0.
When you perform arithmetic on integers
and so this is different than just assigning values assigning it into a float or float to int,
this is when you have an expression,
you're doing some addition some subtraction, whatever the case may be.
When you're doing a subtraction or an addition, you have two operands.
And so one operator can be an int, one operand can be a float.
You have to know how that what conversion is happening.
So if you have two operands in an expression and they're both integers,
then any decimal portion resulting from a division operation is discarded.
So if you do if you have an integer x, that's 20.
You have an integer y, it's 12. And you do 20 divided by 12.
You're not going to get 1 point something something something. You're just going to get 1.
It's going to discard all the results and put it a new because again an int only stores a whole number.
So two numbers are ints and they're doing division.
You're not going to get a floating point number. You're not going to get a decimal number.
Now if one operator is an int and the other is a float,
then the operation is going to be formed as a floating point operation. So if you have float f is 20.0,
float a is 10, an int,
then if you do a division there or 12 I'm sorry that'd be more applicable,
then the result is going to do a floating point number and the result is going to be
1 point 8888 or whatever it is 1 point
whatever the case may be.
You're not assigning this data to anything. This is an expression what is it going to return.
So two ints in a division, it's going to be a whole number.
An int and double or float, it's always going to be a float, it's always going to be a decimal
decimal floating point operation.
And this is the implicit conversion. That's really what you need to understand
what's going on and done for you by the program if you don't do anything.
However, you should try to do some explicit
conversions, which is you can do with the cast operator.
And this is just referred to as casting more or less.
And you see casting in many languages when you want to convert.
And all it is you're doing
explicit conversion, you're saying what you want the data to be.
So you want to do this if you can because otherwise
data might get demoted, it might get lost.
If you do two ints and you're doing division
and they're not divided equally, you're going to lose all that data.
So it's possible for you to demand the precise type conversion that you want
by explicitly specifying it.
This is called a cast and it consists of preceding the quantity
with the name of the desired type in parentheses.
So parentheses and type name
are constitute the
cap operator.
You do a left parenthesis and then you specify the data type and then write parenthesis.
And that's going to convert whatever is to the right of it,
whatever the expression is to the right of it or even if it's just a single variable,
it's going to convert that to what's ever inside the parentheses.
So the actual type is desired such as a long, it's substituted for that word type.
So the type passed operator has a higher precedence than all arithmetic operators
except the unitary minus and unity plus. We haven't learned about precedence yet.
We're going to in the next lecture. Precedence is basically what happens,
the order of the operations that are performed.
So we'll provide some examples of that. All you have to understand at this point is that the typecast operator
takes precedence over every other operator, except two unary minus and unary plus.
So here example, we have a number 21.51
and we have the cast operator because we know it's cast operator because it's in
parentheses and it has a type. And what we're basically saying is
take 21.51 convert it to an int.
If you take a floating point number converted to it,
it just becomes the int, the whole number, 21.
Same it's doing on the right-hand side, it's converting 26.99 to an int.
So what would actually happen here if you did this expression in a statement,
it would evaluate as 21 plus 26. It would
truncate the data from 0.51 to a whole number and the same as 0.99.
And so that's the cast operator, anything inside parentheses that contains a data type.
You'll see this a lot.
If you were to say 21 plus 26 and you cast it into floats,
it would just add a dot 0.
Usually, you don't cast to a more precise type
because you're not going to get more precise.
You cast from more precise type to a less precise.
So more of like a float to an int.
So you'll see this throughout some programs occasionally
when you're using different types. You should try to avoid using different types
if you're doing arithmetic. But if you do, you'll see this.
The size of operator, another operator that's kind of strange,
not similar to a lot of the other ones. And this actually looks like a function.
But the sizeof is an operator. It performs an action.
It's not doing anything function oriented.
What it's doing is it's telling you how many bytes are occupied in memory
by a given type. So it looks like a function because it takes an argument.
And we're going to give an example of that but it's just going to return the number of bytes in memory. Remember that
depending on the system that you're running,
the platform that you're running, the operating system, the architecture of the computer,the hardware,
different data types are going to be represented memory with different sizes.
For example, an int might be 4 bytes on 1 system 8 in another.
So what you can do is you can use the sizeof operator as a special keyword an operator in c
and you can pass in a data type and it will tell you how many bytes it's using in memory.
So sizeof is actually an operator, it's not a function.
It's evaluated at compile time and not at runtime unless a variable length array is used in its argument.
And so we'll mention that. This is basically saying that if you have a variable
that's inside of the sizeof an array,
it's not going to be resolved at compile time at runtime, so
not that important to know.
The argument to the sizeof operator can be a variable, an array name,
the name of a basic data type, like int float,
the name of a derived data type anything or an expression.
So you could say sizeof x plus y.
And that's basically just going to say the sizeof x plus the sizeof y
or the resulting numbers. If x is an int, y is int an it's sizeof 16,
it would say this is an inch 4 bytes.
If it was int one was a float and the result was floating point arithmetic,
then it'd be float is 8 bytes or something.
But you can use it for many things, and you should use it for many things. Sizeof int, for example,
will result in the number of bytes occupied by a variable of type int.
So this would return 4 or 8 depending on your system.
You can also apply the sizeof operator to an expression, as I mentioned,
the result is the size of the value.
That results from the area expression. So if two ints together, they're still going to be an int.
So it's still going to be a size. But you'll see the sizeof operator also being used when we talk about pointers.
I wanted to talk about this now because it's an operator.
But we're going to provide many more examples of this and casting throughout the class
as we talk about more concepts.
Specifically, the sizeof operator comes into play
a lot more when we talk about pointers because
when you're calculating how much memory to allocate which is what pointers are,
you use sizeof because you want to be precise.
But you can use it for other things as well.
So use the sizeof operator whenever possible to avoid having a calculating hard code sizes
into your program.
Hard code sizes magic numbers are not a good thing because again
if you're on a different system, if you were to hard code
4 on 1 system for an int, on the other system might be an 8,
so use sizeof as much as you can and we'll see this come into much more
relatability when we talk about pointers.
Other operators that are a little strange
are the asterisk operator.
You may have said to yourself asterisk, we've already talked about this in multiplication.
But that asterisk takes two operands, one on the left one on the right.
If you apply the asterisk operator
to a variable and you just say star variable name with only one argument
to the right, it represents something else. It's actually represents a pointer.
It's dereferencing a pointer.
And again, this is I'm not going to harp on this now because we're going to go
through this when we talk about pointers.
But if you see something like star a, don't freak out that's actually valid.
That's doing the asterisk the pointer operator.
You may also see the question mark colon.
This is an operator that's used for decision making.
If condition is true, if the thing to the left is true,
then the value to the right after the colon is evaluated and so forth otherwise.
It's a shorthand notation for an if-else statement.
It's a ternary operator, it's called. But again,
I don't want to really discuss these in a lot of detail
now because we're going to talk about these when we talk about our specific
subjects.
We'll talk about the turning operator when we talk about decision statements. We'll talk about the asterisk
operator unary when we talk about pointers.
But if you see this right now and I wanted to mention now because they are technically operators,
but we'll understand their use cases when we talk about those concepts. Thank you.