Is this legal C/C++? `int* p = (int[]) {1,2,3} ;`
It's valid C99 as far as I can tell - that's passing a compound literal.
The C99 standard has this as an example (§6.5.2.5/9):
EXAMPLE 1 The file scope definition
int *p = (int []){2, 4};
initializes p to point to the first element of an array of two ints, the first having the value two and the second, four. The expressions in this compound literal are required to be constant. The unnamed object has static storage duration.
Note that the (int [])
thing is not a cast here.
This is not a valid C++ construct though, compound literals are not part of the C++ standard (C++11 included). Some compilers allow it as an extension. (GCC does, pass -Wall -pedantic
to get a diagnostics about it. IBM xlC allows it as an extension too.)
Why is int x = int(5) legal if int is not a class?
I read though that
int
is not a class and thus has no constructor.
Yes, technically built-in types have no constructor.
what does exactly happen in that line of code
The integer literal 5
is explicitly cast to an int
(a no-op for the compiler mostly) and assigned to x
.
what is the fundamental difference between initialising the int that way and
int x = 5;
Essentially, no difference. All the below expressions are the same in most cases, unless you're a language lawyer (for instance, the last would prevent narrowing i.e. raise an error if the value cannot be represented by the type):
int x = 5; // copy initialization
int y = int(5); // cast and copy initialization
int z = (int)5; // cast and copy initialization
int w(5); // direct initialization
int r{5}; // direct initialization
Read more about initializations for finer details and differences.
Conversion failed when converting the varchar value 'simple, ' to data type int
In order to avoid such error you could use CASE
+ ISNUMERIC
to handle scenarios when you cannot convert to int.
Change
CONVERT(INT, CONVERT(VARCHAR(12), a.value))
To
CONVERT(INT,
CASE
WHEN IsNumeric(CONVERT(VARCHAR(12), a.value)) = 1 THEN CONVERT(VARCHAR(12),a.value)
ELSE 0 END)
Basically this is saying if you cannot convert me to int assign value of 0 (in my example)
Alternatively you can look at this article about creating a custom function that will check if a.value
is number: http://www.tek-tips.com/faqs.cfm?fid=6423
Why does flowing off the end of a non-void function without returning a value not produce a compiler error?
C99 and C++ standards require non-void
functions to return a value, except main
. The missing return statement in main
will be defined (to return 0
). In C++ it's undefined behaviour if execution actually reaches the end of a non-void
function other than main
, while in C it's only UB if the caller uses the return value.
This means functions can look like they might reach the end without returning a value, but actually can't reach the closing }
. John Kugelman's answer shows some examples, like a noreturn function called from one side of an if
. It's only undefined behaviour if execution actually does get to the end without reaching a return
earlier. The rationale includes that checking if every real code path returns a value is quite difficult (without knowing which functions never return), so it's not illegal to compile a function like your example, only to actually call it like your main
does.
As an extension, at least one compiler (MSVC) allows a return value to be set with inline assembly, but most others still require a return statement in functions that use inline asm
.
From C++11 draft:
§ 6.6.3/2
Flowing off the end of a function [...] results in undefined behavior in a value-returning function.
§ 3.6.1/5
If control reaches the end of
main
without encountering areturn
statement, the effect is that of executingreturn 0;
Note that the behaviour described in C++ 6.6.3/2 is not the same in C.
gcc will give you a warning if you call it with -Wreturn-type option.
-Wreturn-type Warn whenever a function is defined with a return-type that
defaults to int. Also warn about any
return statement with no return-value
in a function whose return-type is not
void (falling off the end of the
function body is considered returning
without a value), and about a return
statement with an expression in a
function whose return-type is void.This warning is enabled by -Wall.
Just as a curiosity, look what this code does:
#include <iostream>
int foo() {
int a = 5;
int b = a + 1;
}
int main() { std::cout << foo() << std::endl; } // may print 6
This code has formally undefined behaviour, and in practice it's calling convention and architecture dependent. On one particular system, with one particular compiler, the return value is the result of last expression evaluation, stored in the eax
register of that system's processor, if you disable optimization.
This seems to be a consequence of GCC internals with optimization disabled, because in that case it picks the return-value register if it needs any to implement a statement. With optimization enabled in C++ mode, GCC and clang assume this path of execution is unreachable because it contains undefined behaviour. They don't even emit a ret
instruction, so execution falls into the next function in the .text section. Of course undefined behaviour means that anything could happen.
Good way to encapsulate Integer.parseInt()
You could return an Integer
instead of an int
, returning null
on parse failure.
It's a shame Java doesn't provide a way of doing this without there being an exception thrown internally though - you can hide the exception (by catching it and returning null), but it could still be a performance issue if you're parsing hundreds of thousands of bits of user-provided data.
EDIT: Code for such a method:
public static Integer tryParse(String text) {
try {
return Integer.parseInt(text);
} catch (NumberFormatException e) {
return null;
}
}
Note that I'm not sure off the top of my head what this will do if text
is null. You should consider that - if it represents a bug (i.e. your code may well pass an invalid value, but should never pass null) then throwing an exception is appropriate; if it doesn't represent a bug then you should probably just return null as you would for any other invalid value.
Originally this answer used the new Integer(String)
constructor; it now uses Integer.parseInt
and a boxing operation; in this way small values will end up being boxed to cached Integer
objects, making it more efficient in those situations.
Why assigning an int literal to a byte variable is legal?
Because when you assign a literal(constant value) compiler can prove the value fits in byte. When you assign a variable it can't.
If you assign a constant compiler is more than happy to compile because it can confirm that value is within the range of (0 - 255) which is the valid range for byte
.
For example the following code compiles without any problem.
const int i = 123;
byte b = i;
How to check whether an int variable contains a legal (not trap representation) value?
In C++'s current working draft (for C++20), an integer cannot have a trap representation. An integer is mandated as two's complement: ([basic.fundamental]/3)
An unsigned integer type has the same object representation, value representation, and alignment requirements ([basic.align]) as the corresponding signed integer type.
For each value x of a signed integer type, the value of the corresponding unsigned integer type congruent to x modulo 2N has the same value of corresponding bits in its value representation. 41
[ Example: The value −1 of a signed integer type has the same representation as the largest value of the corresponding unsigned type.
— end example
]
Where the note 41 says
This is also known as two's complement representation.
This was changed in p0907.
Additionally, padding bits in integers cannot cause traps: ([basic.fundamental/4])
Each set of values for any padding bits ([basic.types]) in the object representation are alternative representations of the value specified by the value representation.
[ Note: Padding bits have unspecified value, but do not cause traps.
See also ISO C 6.2.6.2.
— end note
]
Related Topics
Speed Accessing a Std::Vector by Iterator VS by Operator[]/Index
Why Is Taking the Address of a Temporary Illegal
What Happens When C++ Reference Leaves Its Scope
Linking Not Working in Homebrew's Cmake Since Mojave
How to Mark a Struct Template as Friend
Dangling References and Undefined Behavior
Sse2 Intrinsics - Comparing Unsigned Integers
Why Can't a Function Go After Main
How to Convert a Byte Array into Double in C
How Are Objects Stored in Memory in C++
Calling Erase with Iterator VS Const_Iterator
Why Can't I Initialize a Variable-Sized Array
Difference Between Console (/Subsystem:Console) and Windows (/Subsystem:Windows)
Array Decay to Pointer and Overload Resolution
C++ Uniform_Int_Distribution Always Returning Min() on First Invocation