Is the inability to find code by searching for a class name a reason to avoid using auto in c++ variable declarations?

According to https://softwareengineering.stackexchange.com/a/180616/432039 suggested, I know the answer advised “auto” should be used instead of the actual type when declaring variables.

However, the question is about the readability of code before and after using auto, but I found the biggest problem of “auto” is not the readability, instead “auto” hinders me to search the code that I need to fix by using keyword like ‘MyClass ‘ in variable declaration like “MyClass myclass = …”.

For example, suppose I have a c++ mobile game project that needs to load user settings using DTO “UserSettings”, and UserSettings may be loaded from game server, mobile device, or edit by user at some pages, eg (ignore .h and class definition for simpler code):

OldUserLoginPage.cpp

OldUserLoginPage::loadUserData(){
    //some code call http
    UserSettings userSettings=loadUserDataResponse.userSettings;
    //some other code
}

UserResumePage.cpp

UserResumePage::viewDidLoaded(){
    //some init code
    UserSettings userSettings=AppData::getUserSettings();
    //some other init code
}

SettingsPage.cpp

 SettingsPage::onLoadDefaultButtonPressed(){
    //some code
    UserSettings userSettings=DefaultUserSettings::getInstance();
    //some other code
}

When the game works fine over few months, suddenly a use reports that the user settings seems failed to save, and I’m quite sure I would forget about which .cpp contain UserSettings, and also I would forget about loadUserDataResponse.userSettings, AppData::getUserSettings() and DefaultUserSettings::getInstance(), except I know I can search for keyword “UserSettings ” to list all parts of codes that handle user settings.

However, if I just use “auto” instead of UserSettings, I can’t search for keyword “UserSettings ” to find which part of codes that use UserSettings. Although I may also able to find the related code by browsing each .cpp individually after using auto, search for keyword “UserSettings ” helps me a lot faster to find and fix the bug in the code. Also when a new teammate enters the team and start maintaining the code, the teammate may be unable to know which actual page refers to ???Page.cpp immediately, but the new teammate can search for keyword “UserSettings ” to find which part of the code in the project that may contain the bug.

Also even in a single .cpp, I find the type in variable declaration may also help me to find the related code quickly, for example, suppose there is a page about buying items and magic stones:

ShopPage.cpp

ShopPage::method1(){
   //some code
   this->updateTotalCost();
}

ShopPage::method2(){
   //some code
    this->updateTotalCost();
}
.
.
.
ShopPage::updateTotalCost(){
   //some other code
   double totalCost=item1.quanity*item1.price+item2.quanity*item2.price+...
}

Also after some day, suppose some users find the cost seems calculate wrongly, I forgot which function and variable name handles the cost calculating, except I remember the cost must be “double” type, then I can search for “double ” to jump to the related code to investigate the problem.

While I agree “auto” may help me to write the code faster, code is being read and maintained more often than being written, so I would rather write c++ as if “auto” never exists, so that I can search for the code by variable declaration with specific type in order to find and fix the code quickly. So my question is, is the reason above the rationale to avoid using “auto”?

1

No, I don’t think this is a valid reason to avoid all usage of auto in general. It may be a valid reason for certain cases (though both of your examples look somewhat debatable to me).

Let me first say I disagree partially with Herb Sutter’s accepted answer to that other question, that you should use auto as default, as long as you don’t want an explicit conversion. When you read the comments to that answer, you see I am not alone with my opinion, because that strategy can have a negative impact on readability.

The cases where I use auto are mainly the cases where

  • the type name would be unneccessarily repeated on the very same line

  • the exact type name would be something like a longish technical iterator type name and does not really matter

In the first case, usage of auto will not degrade the “global searchability”, and in the second case, it is unlikely you will ever have to make a global search for the type name.

Let me comment on your examples:

  • your second example shows a case where a global search for the type name makes no sense – double is as unspecific as auto. Still, I guess also Herb Sutter would agree to use an explicit type name – in case you want to make sure totalCost has the type double, regardless of what types are used on the right-hand side. That’s what Herb means by “beeing committed to a specific type”.

  • in your first example, I don’t think it is a good strategy to start with a global search for UserSettings when searching the root cause for a certain error. When a save operation “fails”, I would first set a breakpoint into the save operation itself and check if the operation is executed (and fails), or if it is not executed at all. For the latter case, as the next step, I would find out from where I expect the save operation to be called and set breakpoints into all those calling points. A good IDE might show you all potential callers, without such an IDE, a global search for the name of the save operation would be more useful.

    Of course, when your save operation was simply named save, and you have 30 other classes which a member save in your codebase, as a last resort, one could make a global search for UserSettings and hope the returned number of places is smaller than the number of places with the word save in the codebase. But as you see, the global search for a class name is probably not always as useful as it looks like at a first glance.

It’s certainly a valid reason.

Whether that’s enough of a reason to avoid auto in your situation – that depends on whether there are superior reasons for using it. Presumably you can find such reasons in the design documents that led to introducing auto in the first place; here’s a paper by Stroustrup et al. that introduces the concept.

(Personally, I’m a huge fan of type systems doing work that you’d otherwise have to do in your head. So to me, the ideal way of doing type inference would be simply to write “auto” and the IDE replacing it with the type that it has inferenced – which would combine the advantages of both worlds. But apparently not enough people think that to make it happen.)

3

It depends on how clever your development software is. Searching for all uses of MyClass as text is easy. But some IDEs have the ability to search for MyClass as a symbol as well. That could be by using a macro with an expansion containing “MyClass”, use of “super” in a subclass, or any use of “auto” which produces a MyClass, MyClass& and so on.

Now if you want a MyClass instance and nothing else, feel free to use “MyClass” and not “auto”. You do use auto if you don’t really care about the actual type. For example, if a function returns an iterator, that is often a complicated type, and you don’t really care about the type, so you use auto.

It is true that the code is being read and maintained more often than it is written. But that’s at lest one more reason to use auto !

auto as maintenance accelerator – change propagation

For the maintenance of code, auto has indeed often (not always) the advantage of facilitating abstraction and ease decoupling from the types.
Take your example:

double totalCost=item1.quantity*item1.price+item2.quantity*item2.price+....

Imagine that you find out that finally double is not sufficiently precise for the quantity, and you’ need to go for long double to avoid unacceptable loss. You’d have to go carefully through your code, and for every double look if it’s concerned by the change or not. With auto, you let the compiler automatically propagate that change and will have lest risks of forgetting one occurence, which might cost you some runtime approximation that you would not necessarily even notice.

auto as maintenance accelerator – slice protection

But there’s more: auto also avoids nasty slicing errors, when you want to use MySpecialisedClass subclass instead of MyClass and forget to adapt one declarator:

MyClass xyz("some", arguments);
... // lots of code 
MyClass uvw = xyz; // looks fine

But after refactoring:

MySpecialisedClass xyz("some", more, arguments);
... // lots of code 
MyClass uvw = xyz; // still looks fine - but slicing occurs ! 

But what with reading ?

First of all, there are a lot of languages out there with no types specified:

  • Take for example Python, which is strongly but dynamically typed. Python coder usually not complain that their code is difficult to read because the type is not shown explicitly.
  • Take also JavaScript. Do JavaScript complain that their code is not readable ? No, the main concern is when accidentally a variable causes a runtime error because of the wrong type. So the complain is more about type safety than readability.
  • Take some modern languages, like Swift. Swift also encourages type inference and auto-like constructs with let and var.

Why would it be more difficult to read if it’s C++ then ? Because of habit. And habits still prevent people to embrace modern C++ and its benefits.

7

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa
Thiết kế website Thiết kế website Thiết kế website Cách kháng tài khoản quảng cáo Mua bán Fanpage Facebook Dịch vụ SEO Tổ chức sinh nhật