#include <iostream>
#include <map>
using namespace std;
int main() {
map<int, int> ma;
// 원소를 추가 하자!!
ma.insert(make_pair(100, 2)); // key 값 : 1 , value : 3
ma.insert(make_pair(101, 3)); // key 값 : 3, value : 13
ma.insert(make_pair(102, 2)); // key 값 : 3, value : 13
ma.insert(make_pair(103, 3)); // key 값 : 3, value : 13
ma.insert(make_pair(104, 1)); // key 값 : 3, value : 13
// make_pair 형식으로 저장 했으므로
// key 값은 fisrt 로 접근 value 값은 second 로 접근한다.
for (auto iter : ma) {
cout << "key : " << iter.first << " value : " << iter.second << '\n';
iter.second = iter.second 1;
}
cout << "\n" << "\n";
for (auto iter : ma) {
cout << "key : " << iter.first << " value : " << iter.second << '\n';
}
cout << "\n" << "\n";
return 0;
}
Actually , I want to change the value of second component of pair.
iter.second = iter.second 1;
This code can't change the thing... How can I change ???
CodePudding user response:
The auto
keyword in C always tries to infer a non-reference type, so in your case it infers iter
as being type std::pair<const int, int>
. This is not a reference type, so the values from the map get copied into the iter
variable, and so any changes made to iter
are not reflected in the map itself.
You can write auto&
instead to force an lvalue-reference type:
for (auto& iter : ma) { // <-- Notice ampersand here
iter.second = iter.second 1;
}
CodePudding user response:
Your main problem is that you called the variable "iter" so you must think it is an iterator of some sort. If it were an iterator, your code would work fine:
#include <iostream>
#include <map>
int main() {
std::map<int, int> map {
{100, 2}, {101, 3}, {102, 2}, {103, 3}, {104, 1},
};
for (auto iter = map.begin(), end = map.end(); iter != end; iter) {
std::cout << "key : " << iter->first << " value : " << iter->second << '\n';
(iter->second);
}
std::cout << "\n\n";
for (auto iter = map.begin(), end = map.end(); iter != end; iter) {
std::cout << "key : " << iter->first << " value : " << iter->second << '\n';
}
std::cout << "\n\n";
}
But since you are using a range-based for loop you are accessing the values themselves, not an iterator to them. In that case, if you use auto
you are getting a copy of the elements, and any changes you make are done the copies, not the elements themselves. If you instead use auto&
you will get a reference instead, which is what you want:
#include <iostream>
#include <map>
int main() {
std::map<int, int> map {
{100, 2}, {101, 3}, {102, 2}, {103, 3}, {104, 1},
};
for (auto& [key, val] : map) {
std::cout << "key : " << key << " value : " << val << '\n';
val;
}
std::cout << "\n\n";
for (auto& [key, val] : map) {
std::cout << "key : " << key << " value : " << val << '\n';
}
std::cout << "\n\n";
}
Do note the use of structured bindings to simplify the code.