Why I cannot create a simple dictionary here - dictionary

I am trying to create and use a simple dictionary using TFPGmap:
program rnTFPGmap;
{$mode objfpc}
uses fgl;
var
mydict: specialize TFPGmap<string, string>;
key: string;
i: longint;
begin
mydict.create;
mydict.add('k1','v1');
mydict.add('k2','v2');
mydict.add('k3','v3');
//for key in mydict.keys do {does not work either;}
for i := 1 to length(mydict) do {line 17: first error from here. }
writeln(mydict[i]);
end.
However, it is giving following error:
$ fpc soq_rntfpgmap
Free Pascal Compiler version 3.0.0+dfsg-11+deb9u1 [2017/06/10] for x86_64
Copyright (c) 1993-2015 by Florian Klaempfl and others
Target OS: Linux for x86-64
Compiling soq_rntfpgmap.pas
soq_rntfpgmap.pas(17,16) Error: Type mismatch
soq_rntfpgmap.pas(18,19) Error: Incompatible type for arg no. 1: Got "LongInt", expected "ShortString"
soq_rntfpgmap.pas(22) Fatal: There were 2 errors compiling module, stopping
Fatal: Compilation aborted
Error: /usr/bin/ppcx64 returned an error exitcode
Edit: I tried to modify the code according to documentation and came up with following version:
program rnTFPGmap;
{$mode objfpc}
uses fgl;
type
tuple = specialize TFPGmap<string, string>;
mydict = Array of tuple;
var
dict: mydict;
i: tuple;
item: string;
begin
setlength(dict, length(dict)+3);
dict.add('k1','v1'); {error on this line: "CREATE" expected but "ADD" found}
dict.add('k2','v2');
dict.add('k3','v3');
writeln('dict.count: ', dict.count);
for i in dict do
writeln(i);
end.
But I am now getting following error:
$ fpc soq_rntfpgmap
Free Pascal Compiler version 3.0.0+dfsg-11+deb9u1 [2017/06/10] for x86_64
Copyright (c) 1993-2015 by Florian Klaempfl and others
Target OS: Linux for x86-64
Compiling soq_rntfpgmap.pas
soq_rntfpgmap.pas(13,25) Warning: Variable "dict" of a managed type does not seem to be initialized
soq_rntfpgmap.pas(14,7) Fatal: Syntax error, "CREATE" expected but "ADD" found
Fatal: Compilation aborted
Error: /usr/bin/ppcx64 returned an error exitcode
Not able to sort this out.

Following code works. See comments for some explanations:
program rnTFPGmap;
{$mode objfpc}
uses fgl;
type
Rndict = specialize TFPGmap<string, string>;{define type under type}
var
dict: Rndict; {define object under var}
i: integer;
{main: }
begin
dict := Rndict.Create; {create object in main}
dict.add('k1','v1');
dict.add('k2','v2');
dict.add('k3','v3');
for i := 0 to (dict.count-1) do begin
writeln('i: ',i, '; key: ', dict.getkey(i), '; value: ', dict.getdata(i));
end;
end.
Output:
i: 0; key: k1; value: v1
i: 1; key: k2; value: v2
i: 2; key: k3; value: v3
I thank #DavidHeffernan for his guidance.

Related

bus error on usage of rusqlite with spatialite extension

I'm seeing a bus error on cargo run when attempting to load the spatialite extension with rusqlite:
Finished dev [unoptimized + debuginfo] target(s) in 1.19s
Running `target/debug/rust-spatialite-example`
[1] 33253 bus error cargo run --verbose
My suspicion is that there's a mismatch of sqlite version and spatialite and that they need to be built together rather than using the bundled feature of rusqlite, though it seems like that'd result in a different error?
Here's how things are set up:
Cargo.toml
[package]
name = "rust-spatialite-example"
version = "0.0.0"
edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
rusqlite = { version = "0.28.0", features = ["load_extension", "bundled"] }
init.sql
CREATE TABLE place (
id INTEGER PRIMARY KEY,
name TEXT NOT NULL
);
SELECT AddGeometryColumn('place', 'geom', 4326, 'POINT', 'XY', 0);
SELECT CreateSpatialIndex('place', 'geom');
main.rs
use rusqlite::{Connection, Result, LoadExtensionGuard};
#[derive(Debug)]
struct Place {
id: i32,
name: String,
geom: String,
}
fn load_spatialite(conn: &Connection) -> Result<()> {
unsafe {
let _guard = LoadExtensionGuard::new(conn)?;
conn.load_extension("/opt/homebrew/Cellar/libspatialite/5.0.1_2/lib/mod_spatialite", None)
}
}
fn main() -> Result<()> {
let conn = Connection::open("./geo.db")?;
load_spatialite(&conn)?;
// ... sql statements that aren't executed
Ok(())
}
Running:
cat init.sql | spatialite geo.db
cargo run
The mod_spatialite path is correct (there's an expected SqliteFailure error when that path is wrong). I tried explicitly setting sqlite3_modspatialite_init as the entry point and the behavior stayed the same.

Starting .NET Core installer using Inno Setup fails with result code 2

I'm trying to build up an installer using Inno Setup. I need to setup a prerequisite installation for .NET Core framework. By far I'm able to detect .NET Core existence. But I'm having difficulty with executing the installation.
Here's the code I have by far:
[Files]
Source: "\\shared\path\dotnet-runtime-3.1.10-win-x64.exe"; DestDir: "{tmp}"; \
Flags: deleteafterinstall; BeforeInstall: InstallFramework; \
Check: FrameworkIsNotInstalled
[Code]
var
CancelWithoutPrompt: boolean;
InstallValue: Cardinal;
function InitializeSetup(): Boolean;
begin
CancelWithoutPrompt := false;
result := true;
end;
procedure CancelButtonClick(CurPageID: Integer; var Cancel, Confirm: Boolean);
begin
if CurPageID=wpInstalling then
Confirm := not CancelWithoutPrompt;
end;
function FrameworkIsNotInstalled: Boolean;
begin
Result := not RegQueryDWordValue(HKEY_LOCAL_MACHINE,
'SOFTWARE\WOW6432Node\dotnet\Setup\InstalledVersions\x64\sharedfx\Microsoft.NETCore.App',
'3.1.10', InstallValue) or (InstallValue <> 1)
end;
procedure InstallFramework;
var
StatusText: string;
ResultCode: Integer;
begin
StatusText := WizardForm.StatusLabel.Caption;
WizardForm.StatusLabel.Caption := 'Installing .net core framework...';
WizardForm.ProgressGauge.Style := npbstMarquee;
try
if not Exec(ExpandConstant('{tmp}\dotnet-runtime-3.1.10-win-x64.exe'), '/q /norestart', '', SW_SHOW, ewWaitUntilTerminated, ResultCode) then
begin
// you can interact with the user that the installation failed
MsgBox('.NET Core installation failed with code: ' + IntToStr(ResultCode) + '.',
mbError, MB_OK);
CancelWithoutPrompt := true;
WizardForm.Close;
end;
finally
WizardForm.StatusLabel.Caption := StatusText;
WizardForm.ProgressGauge.Style := npbstNormal;
end;
end;
I'm getting result code 2 response from the installation, anyone could enlighten me what's code 2 error about? Or is that any way I could extract further detail on the error information? I tried empty argument and tried to search for Code 2 error information on the internet but still no luck.
I had tried with Shellexec and both return the same result
The installation directly using the .net exe are working fine locally
Any help or information would be much appreciate =)
You are trying to run the dotnet-runtime-3.1.10-win-x64.exe before you actually "install" it to the {tmp}:
BeforeInstall: InstallFramework
You have to use the AfterInstall parameter:
AfterInstall: InstallFramework

Function clause error Erlang

I am trying to understand process communication in erlang. Here I have a master process and five friends process. If a friend sends a message to any of the other 5 they have to reply back. But the master should be aware of all this. I am pasting the code below.
-module(prog).
-import(lists,[append/2,concat/1]).
-import(maps,[from_lists/1,find/2,get/2,update/3]).
-import(string,[equal/2]).
-import(file,[consult/1]).
-export([create_process/1,friends/4, master/1, main/0,prnt/1]).
%% CREATE PROCESS
create_process([])->ok;
create_process([H|T])->
{A,B} = H,
Pid = spawn(prog,friends,[B,self(),0,A]),
register(A,Pid),
create_process(T).
%% FRIENDS PROCESS
friends(Msg, M_pid, State, Self_name)->
S = lists:concat([Self_name," state =",State,"\n"]),
io:fwrite(S),
if
State == 0 ->
timer:sleep(500),
io:fwrite("~p~n",[Self_name]),
lists:foreach(fun(X) -> whereis(X)!{Self_name,"intro",self()} end, Msg),
friends(Msg, M_pid, State + 1, Self_name);
State > 0 ->
receive
{Process_name, Process_msg, Process_id} ->
I = equal(Process_msg,"intro"),
R = equal(Process_msg,"reply"),
XxX = lists:concat([Self_name," recieved ",Process_msg," from ",Process_name,"\n"]),
io:fwrite(XxX),
if
I == true ->
io:fwrite("~p~n",[whereis(Process_name)]),
M_pid!{lists:concat([Self_name," received intro message from ", Process_name , "[",Process_id,"]"]), self()},
io:fwrite(I),
whereis(Process_name)!{Self_name, "reply",self()},
friends(Msg, M_pid, State + 1, Self_name);
R == true ->
M_pid!{lists:concat([Self_name," received reply message from ", Process_name , "[",Process_id,"]"]), self()},
io:fwrite(R),
friends(Msg, M_pid, State + 1, Self_name)
end
after
1000->
io:fwrite(lists:concat([Self_name," has received no calls for 1 second, ending..."]))
end
end.
master(State)->
receive
{Process_message, Process_id} ->
io:fwrite(Process_message),
master(State+1)
after
2000->
ok
end.
main() ->
B = [{john, [jill,joe,bob]},
{jill, [bob,joe,bob]},
{sue, [jill,jill,jill,bob,jill]},
{bob, [john]},
{joe, [sue]}],
create_process(B),
io:fwrite("~p~n",[whereis(sue)]),
master(0).
I think the line in friends() function,
M_pid!{lists:concat([Self_name," received intro message from ", Process_name , "[",Process_id,"]"]), self()}
is the cause of error but I cannot understand why. M_pid is known and I am concatenating all the info and sending it to master but I am confused why it isnt working.
The error I am getting is as follows:
Error in process <0.55.0> with exit value: {function_clause,[{lists,thing_to_list,
[<0.54.0>],
[{file,"lists.erl"},{line,603}]},
{lists,flatmap,2,[{file,"lists.erl"},{line,1250}]},
{lists,flatmap,2,[{file,"lists.erl"},{line,1250}]},
{prog,friends,4,[{file,"prog.erl"},{line,45}]}]}
I dont know what is causing the error. Sorry for asking noob questions and thanks for your help.
An example of what Dogbert discovered:
-module(my).
-compile(export_all).
go() ->
Pid = spawn(my, nothing, []),
lists:concat(["hello", Pid]).
nothing() -> nothing.
In the shell:
2> c(my).
my.erl:2: Warning: export_all flag enabled - all functions will be exported
{ok,my}
3> my:go().
** exception error: no function clause matching
lists:thing_to_list(<0.75.0>) (lists.erl, line 603)
in function lists:flatmap/2 (lists.erl, line 1250)
in call from lists:flatmap/2 (lists.erl, line 1250)
4>
But:
-module(my).
-compile(export_all).
go() ->
Pid = spawn(my, nothing, []),
lists:concat(["hello", pid_to_list(Pid)]).
nothing() -> nothing.
In the shell:
4> c(my).
my.erl:2: Warning: export_all flag enabled - all functions will be exported
{ok,my}
5> my:go().
"hello<0.83.0>"
From the erl docs:
concat(Things) -> string()
Things = [Thing]
Thing = atom() | integer() | float() | string()
The list that you feed concat() must contain either atoms, integers, floats, or strings. A pid is neither an atom, integer, float, nor string, so a pid cannot be used with concat(). However, pid_to_list() returns a string:
pid_to_list(Pid) -> string()
Pid = pid()
As you can see, a pid has its own type: pid().
I ran your code.
Where you went wrong was to pass Process_id(which is of type pid()) to lists:concat/1.
Let us try to understand this error:
{function_clause,[{lists,thing_to_list,
[<0.84.0>],
[{file,"lists.erl"},{line,603}]},
{lists,flatmap,2,[{file,"lists.erl"},{line,1250}]},
{lists,flatmap,2,[{file,"lists.erl"},{line,1250}]},
{prog,friends,4,[{file,"prog.erl"},{line,39}]}]}
It states the function lists:thing_to_list/1 has no definition(see the word function_clause in the error log) which accepts an argument of type pid() as denoted here by [<0.84.0>].
Strings are represented as lists in erlang, which is why we use lists:concat/1.
As #7stud pointed out these are the valid types which can be passed to lists:concat/1 as per the documentation:
atom() | integer() | float() | string()
There are 2 occurrences of the following line. Fix them and you are good to go:
Incorrect Code:
M_pid!{lists:concat([Self_name," received intro message from ", Process_name , "[",Process_id,"]"]), self()},
Corrected Code
M_pid!{lists:concat([Self_name," received intro message from ", Process_name , "[",pid_to_list(Process_id),"]"]), self()},
Notice the use of the function erlang:pid_to_list/1. As per the documentation the function accepts type pid() and returns it as string().

How can I read from the standard error of another program, line by line?

This program catches all of the standard error from another program, but it sometimes gives me a partial line:
#!/bin/env perl6
my $proc = Proc::Async.new('./print_to_stderr');
$proc.stderr.tap( -> $str {
for $str.lines() {
put "Captured ERR: $_";
}
});
my $promise = $proc.start;
await $promise;
Using ./print_to_stderr:
#!/bin/env perl6
for ^10 {
$*ERR.put: "($_): Howdee";
}
Just now, I got the following output:
Captured ERR: (0): Howdee
Captured ERR: (1): Howdee
...
Captured ERR: (6): Howdee
Captured ERR: (7): Howde
Captured ERR: e
Captured ERR: (8): Howdee
As you see, for item 7, the standard error was broken up between two different taps. But I'd like it to wait and give me a whole line.
Update: This was reproducible for me using Rakudo Star 2017.04, but this isn't an issue in Rakudo Star 2017.07 as pointed out by Elizabeth Mattijsen below.
Which version of Rakudo Perl 6 are you using? I cannot reproduce this issue. In any case, Supply.lines should not give you incomplete lines, ever. So if this is happening on the most recent version of Rakudo Perl 6, this should be reported as a bug.

sbt does not differenciate between flags given to test runners

Currently:
Sbt has multiple test runners: scalaTest, junit-interface, etc..
Each test runner has it's own set of flags (scalaTest flags, junit-interface flags).
You can pass flags through sbt to the test runners, for example:
$ sbt '<project>/test-only * -- -f <out_file>' (-f is a scalaTest flag)
However, the flags seem to be passed to all test runners, even if a flag is not compatible with all test runners.
I'm also experiencing behavior contrary to what I found in the documentation. ScalaTest says the -v flag will "print the ScalaTest version" and junit-interface says it will "Log "test run started" / "test started" / "test run finished" events on log level "info" instead of "debug"." Instead ScalaTest throws an unrecognised flag exception.
$ sbt '<project>/test-only * -- -v'
java.lang.IllegalArgumentException: Argument unrecognized by ScalaTest's Runner: -v
at org.scalatest.tools.ArgsParser$.parseArgs(ArgsParser.scala:425)
at org.scalatest.tools.Framework.runner(Framework.scala:929)
...
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at java.lang.Thread.run(Thread.java:748)
[error] (elasticSearchDriver/test:testOnly) java.lang.IllegalArgumentException: Argument unrecognized by ScalaTest's Runner: -v
[error] Total time: 1 s, completed Aug 15, 2017 11:12:56 AM
Question:
What is the actual underlying behavior of the flags passed to the test runners through sbt? Is there a bit of documentation that explains what's going on?
By looking at SBT (0.13.x) we eventually get to a part where:
def inputTests(key: InputKey[_]): Initialize[InputTask[Unit]] = inputTests0.mapReferenced(Def.mapScope(_ in key.key))
private[this] lazy val inputTests0: Initialize[InputTask[Unit]] =
{
val parser = loadForParser(definedTestNames)((s, i) => testOnlyParser(s, i getOrElse Nil))
Def.inputTaskDyn {
val (selected, frameworkOptions) = parser.parsed
val s = streams.value
val filter = testFilter.value
val config = testExecution.value
implicit val display = Project.showContextKey(state.value)
val modifiedOpts = Tests.Filters(filter(selected)) +: Tests.Argument(frameworkOptions: _*) +: config.options
val newConfig = config.copy(options = modifiedOpts)
val output = allTestGroupsTask(s, loadedTestFrameworks.value, testLoader.value, testGrouping.value, newConfig, fullClasspath.value, javaHome.value, testForkedParallel.value, javaOptions.value)
val taskName = display(resolvedScoped.value)
val trl = testResultLogger.value
val processed = output.map(out => trl.run(s.log, out, taskName))
Def.value(processed)
}
}
Notice this line: Tests.Filters(filter(selected)) +: Tests.Argument(frameworkOptions: _*) +: config.options
By reading this I deduce that sbt passes the arguments you pass to it to all the underlying testing frameworks.
Solution
Don't pass test framework flags in your commands. Configure them in your *.sbt files like:
testOptions in Test += Tests.Argument(TestFrameworks.ScalaCheck, "-f")
Documentation on test framework arguments

Resources