As of C++11, when are local variables automatically initialized
If I write
std::vector<int> v;
And then use v somewhere in the function, is automatically v initialized?
When you create an object, it is initialized through a constructor. Every class can have an explicitly defined constructor, and, if no constructor is defined for a class, compiler automatically supplies a default constructor.
In the std::vector case, the defualt constructor of the class will be called, since you are not supplying any arguments.
Related
So, from what I understand, in a class, a self.method is like a class method, whereas a regular method is like an instance method. But, as you can't instantiate a module, why would I use one over the other? What is the difference between these two in a module?
So, from what I understand, in a class, a self.method is like a class method, whereas a regular method is like an instance method.
That is not true. Ruby only has one single kind of method: instance methods. So, what you call a "regular method" is not "like" an instance method, it is an instance method. And there are no class methods in Ruby, every method is an instance method.
There are two ways to define a method in Ruby: with an explicit definee (def foo.bar) and without (def bar, which is then using the default definee).
In the first case, it is easy to know where a method will be defined: if you say def foo.bar, the method will become an instance method of foo's singleton class, always.
If you say def bar, the method becomes an instance method of the default definee, which usually, but not always, is the closest lexically enclosing module definition body. The most notable exception is a method that is defined directly in a script body, in this case, there is no lexically enclosing module definition, and the default definee is Object instead. In fact, there is even another twist: the method will be implicitly defined as private as well.
So, in your case, the first method will become an instance method of the singleton class of self (and inside a module definition body, self is the module itself), the second method will become an instance method of the module.
But, as you can't instantiate a module,
Ruby has a feature called inheritance. While it is true that you can directly instantiate a module, you can instantiate a class that inherits from a module. In fact, since the Object class inherits from the Kernel module (which has instance methods like Kernel#puts or Kernel#require, which may have used once or twice), and almost every class directly or indirectly inherits from Object, it is highly likely that you will have in your Ruby programming already have instantiated an indirect instance of a module and used a module's instance methods.
Enumerable is another important module in Ruby that contains methods like map, select, etc. that both Array and Hash inherit from.
why would I use one over the other?
There's really not much to it: you'd use an instance method, if you want to … well use an instance method, i.e. want to have a method that has privileged access to the internal representation of self across many different instances of the same module.
You would use a method of the singleton class, if you want the method to be only available for that single object.
There is one and only one reason for having module methods: to invoke those methods on the module in which they defined (using self: def self.my_method...). An example of this is Ruby's built-in Math module. All methods in this module are module methods. These methods are all invoked with Math as their explicit receiver (e.g., Math.sqrt(2.5)). In effect, they are used like functions in non-OO languages.
When you include, prepend or extend a module from a class, any module methods are simply ignored.
You might find this (timely) article helpful in understanding the Ruby object model and how methods are “looked up”: https://www.honeybadger.io/blog/ruby-method-lookup/
I have a class Bar which implements a move constructor.
For an instance Bar b, if I call void fooRvalRef(Bar&&) using fooRvalRef(std::move(b)) then the move constructor of Bar is not called.
On the other hand for the function void foo(Bar), calling it using foo(std::move(b)) calls the move constructor of Bar.
Why is that?
std::move tries to turn the argument into an rvalue reference, that's all it does, it doesn't move the object. Since it succeeds in your fooRvalRef call, there is no need for a move constructor, it simply passes the rvalue reference to the rvalue-reference parameter.
In the case of foo(Bar) you're passing by value so, ordinarily, the copy constructor would be called. However in this case you have a move constructor and you are passing an rvalue reference, thanks to std::move, so the move constructor is called.
This question already has answers here:
Ruby metaclass confusion
(4 answers)
Closed 7 years ago.
I don't quite get some things about the Ruby object model. First, is EVERYTHING in Ruby an instance of Class? These all produce true:
p Object.instance_of?(Class)
p Class.instance_of?(Class)
p Module.instance_of?(Class)
p BasicObject.instance_of?(Class)
class Hello; end
p Hello.instance_of?(Class)
I can't quite get how is it possible, if Object is a superclass of Class, how can it be both a superclass of Class and an instance of it at the same time (most diagrams on the Ruby Object Model clearly state this hierarchy)? Which allows for some crazyness like this:
p BasicObject.is_a?(Object) #=> true
where BasicObject.class is Class, and Class.is_a?(Object).
By the way, using Ruby 2.0.
First, is EVERYTHING in Ruby an instance of Class?
No, not everything is an instance of Class. Only classes are instances of Class.
There are lots of things which aren't instances of Class: strings, for example, are instances of String, not Class. Arrays are instances of Array, integers are instances of Integer, floats are instances of Float, true is an instance of TrueClass, false is an instance of FalseClass, nil is an instance of NilClass, and so on.
Every class is an instance of Class, just like every string is an instance of String.
if Object is a superclass of Class, how can it be both a superclass of Class and an instance of it at the same time (most diagrams on the Ruby Object Model clearly state this hierarchy)?
Magic.
Just like in most other languages, there are some core entities that are simply assumed to exist. They fall from the sky, materialize out of thin air, magically appear.
In Ruby, some of those magic things are:
Object doesn't have a superclass, but you cannot define a class with no superclass, the implicit direct superclass is always Object. [Note: there may be implementation-defined superclasses of Object, but eventually, there will be one which doesn't have a superclass.]
Object is an instance of Class, which is a subclass of Object (which means that indirectly Object is an instance of Object itself)
Class is a subclass of Module, which is an instance of Class
Class is an instance of Class
None of these things can be explained in Ruby.
BasicObject, Object, Module and Class all need to spring into existence at the same time because they have circular dependencies.
Just because this relationship cannot be expressed in Ruby code, doesn't mean the Ruby Language Specification can't say it has to be so. It's up to the implementor to figure out a way to do this. After all, the Ruby implementation has a level of access to the objects that you as a programmer don't have.
For example, the Ruby implementation could first create BasicObject, setting both its superclass pointer and its class pointer to null.
Then, it creates Object, setting its superclass pointer to BasicObject and its class pointer to null.
Next, it creates Module, setting its superclass pointer to Object and its class pointer to null.
Lastly, it creates Class, setting its superclass pointer to Module and its class pointer to null.
Now, we can overwrite BasicObject's, Object's, Module's, and Class's class pointer to point to Class, and we're done.
This is easy to do from outside the system, it just looks weird from the inside.
You should notice that:
p BasicObject.instance_of?(BasicObject)
prints false.
That is, the expression BasicObject is not an instance of BasicObject, it is an instance of something else, that is, it is a Class object, which represents an object that holds (for example) the class methods, such as new.
For example:
p (BasicObject.new()).instance_of?(BasicObject)
prints true, and
p (BasicObject.new()).instance_of?(Class)
prints false.
All of your examples were by definition classes. Classes are also objects. But what you didn't do was look at an instance of a class:
p Object.new.class
p Hello.new.class
Classes define the form of an object, and by definition, a class is a Class. But when you instantiate class into an object, the object is the new type. But you can still see that the object's class is itself Class:
p Hello.new.class.class
Do I need to explicitly initialize an object if an initialize method is included in class definition?
No, Ruby does not call initialize automatically.
The default implementation of Class#new looks a bit like this:
class Class
def new(*args, &block)
obj = allocate
obj.initialize(*args, &block)
obj
end
end
[Actually, initialize is private by default so you need to use obj.send(:initialize, *args, &block).]
So, the default implementation of Class#new does call initialize, but it would be perfectly possible (albeit extremely stupid) to override or overwrite it with an implementation that does not.
So, it's not Ruby that calls initialize, it's Class#new. You may think that's splitting hairs, because Class#new is an integral part of Ruby, but the important thing here is: it's not some kind of language magic. It's a method like any other, and like any other method it can be overridden or overwritten to do something completely different.
And, of course, if you don't use new to create an object but instead do it manually with allocate, then initialize wouldn't be called either.
There are some cases where objects are created without calling initialize. E.g. when duping or cloneing, initialize_dup and initialize_clone are called instead of initialize (both of which, in turn, call initialize_copy). And when deserializing an object via, say, Marshal, its internal state is reconstructed directly (i.e. the instance variables are set reflectively) instead of through initialize.
Yes, it's called from new method, which you use to create objects.
It depends on your definition of "explicit". Usually you need to, even if there are no arguments:
object = MyClass.new(...)
In some cases there are factory methods that produce instances you can use, creating a form of implicit initialization:
object = MyClass.factory_method(...)
This would have the effect of calling MyObject.new internally.
There are some libraries which have rather unusual method signatures, like:
object = MyClass(...)
object = MyClass[...]
The effect is the same, as these might look odd but are just method calls.
I understand that local variables are limited to the scope they were declared in and instance variables exist as long as the class exists, but what happens if you declare a local variable in the class scope without prefixing it with #? Doesn't that implicitly it is an instance variable, even though you didn't use an # to declare it as one?
instance variables exist as long as the class exists
They exist as long as the object exist. Instance variables are per-object, not per-class.
what happens if you declare a local variable in the class scope without prefixing it with #?
Then the variable is in scope within the class definition, but not within any defs inside that class definition as those introduce a new scope.
Doesn't that implicitly make it an instance variable, even though you didn't use an # to declare it as one?
No.
If you use define_method instead of def to create methods, the local variable will be accessible within the methods, but since the variable only exists once (not once per object), they'd act more like class variables than instance variables in that case. I also can't think of a good reason why you'd use them that way.
Using #makes it an instance variable for an object that you create. When you are doing things with that object you can set local variables but they disappear after use. Instance variables will stay around as long as there is an object.