程序员问答大本营 98sky.com.


10 questions online user: 19

9
votes
answers
26 views
+10

Why C and Java round floats differently?

Consider the floating point number 0.644696875 lets convert it to a string with eight decimals using Java and C:

Java

import java.lang.Math;
public class RoundExample{
     public static void main(String[] args){
        System.out.println(String.format("%10.8f",0.644696875));
     }
}

result: 0.64469688

try it yourself: http://tpcg.io/oszC0w

C

#include <stdio.h>

int main()
{
    printf("%10.8f", 0.644696875); //double to string
    return 0;
}

result: 0.64469687

try it yourself: http://tpcg.io/fQqSRF

The Question

Why is the last digit different?

Background

The number 0.644696875 cannot be represented exactly as a machine number. It is represented as the fraction 2903456606016923 / 4503599627370496 which has a value of 0.6446968749999999

This is admittedly an edge case. But I am really curious as to the source of the difference.

Related: https://mathematica.stackexchange.com/questions/204359/is-numberform-double-rounding-numbers

8
votes
answers
6 views
+10

Where to put using directives in C++ header files

For my project I am using some pretty convoluted data structures, e.g.

std::unordered_map<int, std::list<std::shared_ptr<const Foo>>>

for which I would like to declare type aliases for readability. The code on which I built my project on already did this by putting using statements globally in the header files:

// bar.h
#ifndef BAR_H
#define BAR_H

#include <unordered_map>
#include <list>
#include <memory>
#include "foo.h"

using FooTable = std::unordered_map<int, std::list<std::shared_ptr<const Foo>>>;

class Bar {
    FooTable create_foo();
};

#endif

Since my C++ knowledge was a little rusty, I just adopted this style -- but now I read that using using in that way can be problematic, since it forces this alias on everything that includes this header.

Despite a good amount of googling, I could not find a concrete answer on how to handle this properly, only lots of statements on what not to do. So, I just put the using inside the class:

// bar.h
#ifndef BAR_H
#define BAR_H

#include <unordered_map>
#include <list>
#include <memory>
#include "foo.h"


class Bar {
    using FooTable = std::unordered_map<int, std::list<std::shared_ptr<const Foo>>>;

    FooTable create_foo();
};

#endif

However this has the drawback, that I need to restate the alias in the source file:

// bar.cpp
#include "bar.h"

using FooTable = std::unordered_map<int, std::list<std::shared_ptr<const Foo>>>;

FooTable Bar::create_foo()
{
...
}

While this seems to work, I am not sure whether this is safe... and my gut tells me it is kind of ugly. So before I rewrite my whole project like this I thought I'd ask: Is a there a better/more elegant/safer way to do this? Or should I just refrain from using type aliases in header files completely?

10
votes
answers
18 views
+10

Remove double quotes if delimiter value is not present in data

An input file is given, each line of which contains quotes for each column and carriage return/ new line character.

  • If the line contains new lines it has be appended with in the same line which is inside the quotes i.e for example line 1

  • Removing of double quotes for each column if the delimiter(,) is not present.

  • Removing of Carriage Return characters i.e(^M)

To exemplify, given the following input file

"name","address","age"^M
"ram","abcd,^M
def","10"^M
"abhi","xyz","25"^M
"ad","ram,John","35"^M

I would like to obtain the following output by means of a sed/perl/awk script/oneliner.

name,address,age
ram,"abcd,def",10
abhi,xyz,25
ad,"ram,John",35

Solutions which i have tired it so far For appending with previous line

sed '/^[^"]*"[^"]*$/{N;s/
//}' sample.txt

for replacing control-m characters

perl -pne 's/\r//g' sample.txt

But i didn't achieve final output what i required below

10
votes
answers
8 views
+10

Why is this C++ fold expression valid?

On cppreference, I saw that there are four types of fold expressions, unary right, unary left, binary right, and binary left. What is the type of this fold expression here? I'm having a hard time understanding why it is valid.

    template <typename Res, typename... Ts>
    vector<Res> to_vector(Ts&&... ts) {
        vector<Res> vec;
        (vec.push_back(ts) ...); // *
        return vec;
    }

What is the value of "pack", "op" and "init" in line *, if any?

This example is from page 244 of Bjarne Stroustrup's A Tour of C++ book, and seems like a comma was forgotten in the example, hence my confusion.

13
votes
answers
8 views
+10

Why do I get 38528 when casting 10000000 to char?

Java uses 32 bits for the char tipe - so the max value is 65536.

But the following code give me the result reported in the title.

public static void main(String[] args) {
    int a = 10000000;
    char b = 33;
    b = (char)a;
    System.out.println((int)b);

}
12
votes
answers
24 views
+10

Ada - Nullable type

How can I initialize a custom type to null ?

I want to do this :

TestVar : T_MyType := null;

With :

type T_MyType is
record
    field1 : float
    field2 : Boolean
end record

But I have an error :

expected type "T_MyType" defined at myfile.ads

11
votes
answers
4 views
+10

How C structures get passed to function in assembly?

1)How C structures get passed to function in assembly. I mean pass by value, not pass by reference. 2)By the way, how callees return structure to its callers? I'm so sorry for the poor expression since I'm not a native English speaker.

I wrote a simple program to testify how C structures get passed to function. But the result was quite surpirsed. Some value was passed by register, but some value was passed by pushing them into stack. Here is the code.

source code

#include <stdio.h>

typedef struct {
        int age;
        enum {Man, Woman} gen;
        double height;
        int class;
        char *name;
} student;

void print_student_info(student s) {
        printf("age: %d, gen: %s, height: %f, name: %s
", 
                        s.age,
                        s.gen == Man? "Man":"Woman",
                        s.height, s.name);
}

int main() {
        student s;
        s.age = 10;
        s.gen = Man;
        s.height = 1.30;
        s.class = 3;
        s.name = "Tom";
        print_student_info(s);
        return 0;
}

asm

 6fa:   55                      push   %rbp
 6fb:   48 89 e5                mov    %rsp,%rbp
 6fe:   48 83 ec 20             sub    $0x20,%rsp
 702:   c7 45 e0 0a 00 00 00    movl   $0xa,-0x20(%rbp)
 709:   c7 45 e4 00 00 00 00    movl   $0x0,-0x1c(%rbp)
 710:   f2 0f 10 05 00 01 00    movsd  0x100(%rip),%xmm0        # 818 <_IO_stdin_used+0x48>
 717:   00 
 718:   f2 0f 11 45 e8          movsd  %xmm0,-0x18(%rbp)
 71d:   c7 45 f0 03 00 00 00    movl   $0x3,-0x10(%rbp)
 724:   48 8d 05 e5 00 00 00    lea    0xe5(%rip),%rax        # 810 <_IO_stdin_used+0x40>
 72b:   48 89 45 f8             mov    %rax,-0x8(%rbp)
 72f:   ff 75 f8                pushq  -0x8(%rbp)
 732:   ff 75 f0                pushq  -0x10(%rbp)
 735:   ff 75 e8                pushq  -0x18(%rbp)
 738:   ff 75 e0                pushq  -0x20(%rbp)
 73b:   e8 70 ff ff ff          callq  6b0 <print_student_info>
 740:   48 83 c4 20             add    $0x20,%rsp
 744:   b8 00 00 00 00          mov    $0x0,%eax
 749:   c9                      leaveq 
 74a:   c3                      retq   
 74b:   0f 1f 44 00 00          nopl   0x0(%rax,%rax,1)   

I expected structure was passed to function using the stack, but the code above showed it wasn't.

11
votes
answers
2 views
+10

Task on the number of iterations

There is a number N every iteration it becomes equal to (N*2)-1 I need to find out how many steps the number will be a multiple of the original N;

( 1≤ N ≤ 2 · 10 9 )

For example:

N = 7; count = 0

N_ = 7*2-1 = 13; count = 1; N_ % N != 0

N_ = 13*2-1 = 25; count = 2; N_ % N != 0

N_ = 25*2-1 = 49; count = 3; N_ % N == 0 

Answer is 3

if it is impossible to decompose in this way, then output -1

       #include <iostream> 
       using namespace std;

       int main(){
           int N,M,c;
           cin >> N;
           if (N%2==0) {
               cout << -1;
               return 0;
           }
           M = N*2-1;
           c = 1;
           while (M%N!=0){
               c+=1;
               M=M*2-1;
           }
           cout << c;
           return 0;
       }

It does not fit during (1 second limit). How to optimize the algorithm?

P.S All the answers indicated are optimized, but they don’t fit in 1 second, because you need to change the algorithm in principle. The solution was to use Euler's theorem.

12
votes
answers
8 views
+10

Unclear casting in C [on hold]

I was surprised why I get different results.

    uint16_t wCaptureTime = 35;

    wDeltaTime1 = (uint16_t) - (int16_t)wCaptureTime;
    wDeltaTime2 =  0xFFFF - (int16_t)wCaptureTime;

    printf("wDeltaTime1 %d 
", wDeltaTime1);
    printf("wDeltaTime2 %d 
", wDeltaTime2);

The code results in:

wDeltaTime1 65501 
wDeltaTime2 65500 

Could someone explain or give some link to read about that behaviour.

10
votes
answers
8 views
+10

Do not add to list if it is null c# [on hold]

I am trying to create a list from anonymous function. I want the list to be created if request model properties are not null. Currently, it is adding null to the list

Code

public void method (RequestModel request)
{
 var create = new DtoModel
     {
        docs= new List<docsModel>
         {
           request.FirstDoc!= null ? runFunction(request.FirstDoc) :null,
           request.SecondDoc!= null ? runFunction(request.SecondDoc) : null,
           request.ThirdDoc!= null ? runFunction(request.ThirdDoc) : null,
          }
     };
}

Currently, it is creating a list of count 3 even if any of the docs are null. I would list to be only created if docs are not null and the list should only contain docs that are not null. There should not be any null values. Request model can have x number of docs.

I know I can use Linq to remove nulls afterwards but I am looking for a solution where it does not create null elements in list.