my "hello world" program in python and C/C++ take about 7 seconds to run . what should i do
python
print("Hello world!")
and
C++
#include<iostream>
using namespace std;
int main() {
cout << "Hello world!";
return 0;
}
Related
I have C code in which I am calling golang functions. I am able to do it for primitives data types (int/float etc.) but I want to return some other data structure like array/list/slice.
I could not find any solution on internet.
Looking for help.
Want to return a array/slice/list of string data type.
It would be helpful if you provide additional information, i.e. example code you are currently working on.
As stated from the Cgo documentation page:
Go array types are not supported; use a C pointer
To do so
hello.go
package main
// #include <stdlib.h>
import "C"
import "unsafe"
// StringSlice is a wrapper arround GoStringSlice to make it usable in C.
//export StringSlice
func StringSlice() **C.char {
x := GoStringSlice()
ret := C.malloc(C.size_t(len(x)) * C.size_t(unsafe.Sizeof(uintptr(0))))
// convert to usable format so we are able to fill it with data
pRet := (*[1<<30 - 1]*C.char)(ret)
for i, item := range x {
pRet[i] = C.CString(item)
}
return (**C.char)(ret)
}
func GoStringSlice() []string {
return []string{
"Hello",
"World",
}
}
func main() {}
hello.c
#include <stdio.h>
#include "hello.h"
int main() {
printf("Hello from C!\n");
char **slice = StringSlice();
int numItems = sizeof(slice) / sizeof(char *);
printf("Number of items: %d\n", numItems+1);
printf("String #0: %s\n", *slice);
slice++;
printf("String #1: %s\n", *slice);
return 0;
}
You have to execute go build -buildmode=c-archive hello.go which will generate a hello.h and hello.a.
The hello.a has to be compiled with your C code: gcc -pthread hello.c hello.a -o hello.
I have following go-code:
package main
import "fmt"
type foo struct {
bar string
some int
}
//go:noinline
func sum(a int, b int) {
fmt.Printf("Sum: %d\n", (a + b))
}
//go:noinline
func (f *foo) baz(value string) string {
return f.bar
}
//go:noinline
func (f *foo) nested(_f foo) foo {
fmt.Printf("Arg value: %s and %d\n", _f.bar, _f.some)
return _f
}
func main() {
f := foo{
bar: "hello world!",
some: 42,
}
fmt.Println(f.baz(f.bar))
sum(1, 2)
temp := f.nested(f)
fmt.Println(temp.bar)
}
Following script or I have problems to dereference the string struct correctly when using a struct definition:
struct args
{
uint64_t array;
uint64_t length;
uint64_t somevalue;
};
uprobe:/tmp/main:0x49aa00 {
$s = (struct args *)(reg("sp") + 16);
$length = *(reg("sp") + 24);
$array = reg("sp") + 16;
printf("length: %d\n", $s->length);
printf("array: %s\n", str(*($array), $length));
printf("somevalue: %d\n", $s->somevalue);
// this one will be empty
printf("array: %s\n", str($s->array, $s->length));
}
Output:
Attaching 1 probe...
length: 12
array: hello world!
somevalue: 42
array:
Removing $s->length prints 64 bytes (default) however:
hello world!host is downillegal seekinvalid slotlfstack.pushmad
Using reg("sp") works without any issues but when using a user-defined struct the array seems to be "empty". $s->length seems to be 12 but when assigning to an additional variable it becomes 2... Can someone help out here, please?
I have tested your code with bpftrace 0.9.4 in ubuntu 20.04, it seems the same issue.
After that I build bpftrace with latest version, all is ok.
You can have a try.
Attaching 1 probe...
length: 12
array: hello world!
somevalue: 42
array: hello world!
I was asked this question and could not come up with a solution, hope to find it here.
We need a function that receives a number (X) and a string, it needs to print that string X number of times, without using any loops or if-else conditions.
It's more about a generic algorithm not a specific programming language.
My initial response was recursion, but it requires an IF clause.
func (int x, string namme)
{
if(x>0)
{
print (name);
func(x-1);
}
}
In general case, you cannot do that. Even recursion's terminal case requires condition. The only solution in such case is ... Template magic (surprise!)
Here is the solution:
template <int times>
void print(const string& str);
template <>
void print<0>(const string& str)
{
}
template <int times>
void print(const string& str)
{
cout << str << " ";
print<times - 1>(str);
}
Such approach requres from you compile time value of number of times. But result code will not contain any conditions (you can see asm code)
Example of usage:
print<5>("Yeah!");
You can use a little trick in c++:
ยง4.7/4 (Integral Conversion)
If the source type is bool, the value false is converted to zero and the value true is converted to one.
This means you can index an array using a boolean value. If your array contains function pointers you implemented an if/else statement.
void noop(int,std::string) {}
void print_n_times(int times, std::string text) {
void (*next_function[])(int,std::string) = {
noop,
print_n_times
};
next_function[(times-1)>0](times-1, text);
std::cout << times << ' ' << text << '\n';
}
See it live
You can do the same thing in python:
Python 2.7.12 (default, Oct 10 2016, 12:56:26)
[GCC 5.4.0] on cygwin
Type "help", "copyright", "credits" or "license" for more information.
>>> def noop(times,text):
... pass
...
>>> def print_n_times(times,text):
... next_function = [noop, print_n_times]
... print(text);
... next_function[int((times-1)>0)](times-1, text)
...
>>> print_n_times(4, "Hello World!")
Hello World!
Hello World!
Hello World!
Hello World!
Here is a complete program demonstrating this. I would not recommend writing anything like this in Real Life.
This takes advantage of the fact that subtracting 1 from 0 will set the most significant bit in an integer. I shift bit 63 down to 0 to get either a 1 or 0 (i.e. to avoid a conditional) and call one of two functions. runtime.Goexit will terminate a goroutine, but will call all deferred functions in the process. This unlocks a mutex that lets the sillyString function terminate only after all of the prints have happened.
package main
import (
"fmt"
"runtime"
"sync"
)
func main() {
sillyString("omg", 10)
}
func sillyString(s string, n int) {
var m sync.Mutex
m.Lock()
go func() {
defer m.Unlock()
mustGoDeeper(s, uint64(n-1), []func(){runtime.Goexit, func() {}})
}()
m.Lock()
}
func mustGoDeeper(s string, n uint64, fs []func()) {
sig := (1 - int(n>>63))
fs[sig]()
fmt.Printf("%s\n", s)
mustGoDeeper(s, n-1, fs)
}
Recursion looks like a good way to go, but we need to stop an infinite recursion. That means being sneaky. Using a try ... catch can do the job, at least in a language which supports that construct:
void printXtimes(String text, int x) {
try {
int z = 100 / x;
} catch (Exception ex) {
// Zero divide so exit program.
exit(0);
}
println(text);
printXtimes(text, x-1);
} // end printXtimes()
That is a Java-like pseudocode. In real Java the compiler gives a warning about infinite recursion, but it compiles and runs correctly, printing the text message the given number of times. An interesting problem.
I want to malloc large number of objects in to memory.(about 100 million objects) because the gc of golang is not effective enough,so i need to use c/c++ to malloc memory and use std::vector to hold objects.
this is my code,i want use std container in cgo:
package main
import (
"fmt"
)
/*
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <vector>
using namespace std;
void dosome(){
vector<int> ivec; // empty vector
for (vector<int>::size_type ix = 0; ix != 10; ++ix)
ivec[ix] = ix; // disaster: ivec has no elements
}
*/
// #cgo LDFLAGS: -lstdc++
import "C"
//import "fmt"
func main() {
C.dosome()
var input string
fmt.Scanln(&input)
}
and have error message below:
go run stddemo.go
# command-line-arguments
./stddemo.go:13:10: fatal error: 'vector' file not found
#include <vector>
^
1 error generated.
how can i set the include path or is there another idea?
While you can use C++ with CGo, you can't embed that code inside the .go file, since it ultimately gets built with a C compiler.
Instead, place your dosome function in a separate .cpp file in the same directory as the .go file, and declare your function to use C linkage. For example:
extern "C" {
void dosome() {
vector<int> ivec;
...
}
}
If you include a prototype for the function in the CGo comment in the .go file so you can call it from Go.
Since you have multiple files now, you can't use the go run foo.go shorthand any more (since it only compiles a single file). Instead, you will need to use go run package or go build package, where your code is located at $GOPATH/src/package.
Uhh I think your conclusions are a bit too fast. GC cost is driven by two things: The more garbage your program produces, the more the GC will have to run. Second: The more pointers there are to scan, the longer a single GC will take.
That is to say: as long as you put your 100 million things into a go slice and keep them there: the GC won't have to run much, because there's no garbage. And second: if your things don't contain pointers, GC time, should it still occur, will be fine.
So, my question is: do your things have pointers?
if you just want to call someone's golang code this is a quick ram inefficient way:
package main
import "C"
import "fmt"
import "unsafe"
func intArrayFromC (src unsafe.Pointer, sz int) []uint64 {
dest := make([]uint64, sz)
copy(dest, (*(*[1000000000]uint64)(unsafe.Pointer(src)))[:sz:sz])// big number dose not affect ram.
return dest
}
//export doPrint
func doPrint(src unsafe.Pointer, sz int){
var numbers []uint64 = intArrayFromC(src, sz);
for i := 0; i < len(numbers); i++ {
fmt.Printf("%d index: %d\n", numbers[i], i)
}
}
func main() {}
and the c++ code:
#include "print.h"
#include <string.h>
#include <vector>
int main() {
std::vector<GoUint64> numbers{99,44,11,00,2,33,44};
while (1) {
doPrint(numbers.data(), numbers.size());
}
return 0;
}
example files
src/test.go
package main
import (
. "clib"
)
func main() {
a := "123";
b := "456";
c := "789";
println(a,b,c);
Output("ABC");
}
src/clib/clib.h
#ifndef CLIB
void output(char* str);
#endif
src/clib/clib.c
#include "clib.h"
#include <stdio.h>
void output(char* str)
{
printf("%s\n", str);
}
src/clib/clib.go
package clib
/*
#cgo CFLAGS:-g
#include "clib.h"
*/
import "C"
func Output(s string) {
p := C.CString(s);
C.output(p);
}
exec code
go build -gcflags "-N -l" test.go
gdb ./test
b 10
r
info locals // <- every variable's value is wrong!
Who can help me solve this problem, thank you very much.
My Environment:
ubuntu 11.04 i386
gdb 7.6
go 1.1
There is currently an open bug regarding this: https://code.google.com/p/go/issues/detail?id=5221
Debugging cgo with gdb worked in 1.0 but is currently broken in 1.1. It's being worked on.