platelet's blog

By platelet, history, 14 months ago, In English

Wrong answer submission and Accepted submission

You can compare them, the only difference is that the Wrong answer submission has an extra cin.tie(0)->sync_with_stdio(0);

I didn't use cin and cout, just fread and fwrite.

Can someone tell me if there is something wrong with my usage or a compiler bug.

  • Vote: I like it
  • +28
  • Vote: I do not like it

»
14 months ago, # |
Rev. 2   Vote: I like it 0 Vote: I do not like it

https://cplusplus.com/reference/ios/ios/tie/

The second form (2) ties the object to tiestr and returns a pointer to the stream tied before the call, if any.

In other words, cin.tie does not return &cin for ->sync_with_stdio(0) to operate on. Instead, it returns the C stdin. You can confirm this by running the program

#include <iostream>

using namespace std;

int main() {
    cout << "cin address = " << (&cin) << endl;
    cout << "cie.tie address = " << cin.tie(0) << endl;
}

For me, it output

cin address = 0x4660
cin.tie address = 0x4710

EDIT: This was not the error, see below.

  • »
    »
    14 months ago, # ^ |
    Rev. 2   Vote: I like it +16 Vote: I do not like it

    sync_with_stdio is a static function of class ios, so cin.tie(0)->sync_with_stdio(0) is equivalent to cin.tie(0), ios::sync_with_stdio(0).

    • »
      »
      »
      14 months ago, # ^ |
        Vote: I like it 0 Vote: I do not like it

      I see, so that wasn't the issue.

      I've played around with your code a bit. Haven't found a solution yet, but there might be some ordering issue with the commas. See this submission where I just changed a comma and got it to error at the 94684 number instead of the 47312 number. This might be a situation where C++'s optimizer might be screwing things by re-ordering things around.

      • »
        »
        »
        »
        14 months ago, # ^ |
          Vote: I like it -8 Vote: I do not like it

        94684 is about twice 47312, I think the reason for this is that you changed inSZ from 1 << 17 to 1 << 18, so I still think it's cin.tie(0)->sync_with_stdio(0) that's causing the fread error.

    • »
      »
      »
      14 months ago, # ^ |
        Vote: I like it +51 Vote: I do not like it

      OK, I found your error. Using cin.tie and sync_with_stdio after fread is undefined behavior, and you used fread within your IO constructor.

      See this submission. the only change is that I used new to allocate your code so the constructor happens AFTER the cin functions.

»
14 months ago, # |
  Vote: I like it +8 Vote: I do not like it

One way of fixing this is by making dummy methods in your IO struct, and defining cin and cout as macros to your IO struct. For example, my IO struct in this submission uses the same idea and functions as a drop-in replacement for my template that has cin.tie(nullptr)->sync_with_stdio(false) for all practical purposes (other than interactive problems, of course).