I have similar algorithm but shorter code. The first scan to find initial positions for mx_id and mn_id, if they exist. Second scan to find real mx_id. Third scan to find real mn_id. The reasoning is to use right most largest number to swap left most number that is smaller than the max.

int maximumSwap(int num) {
string s=to_string(num);
int mxid=-1,mnid=-1;
for (int i=1;i<s.size();i++) {
if (s[i]>s[i-1]) {
mxid=i;
mnid=i-1;
break;
}
}
if (mxid==-1) return num;
for (int i=mxid+1;i<s.size();i++) {
if (s[i]>=s[mxid]) {
mxid=i;
}
}
for (int i=0;i<=mnid;i++) {
if (s[i]<s[mxid]) {
swap(s[i],s[mxid]);
return stoi(s);
}
}
}