How is syntax used in a program? - stata

I have used the program command in Stata quite a few times now.
Today, I am trying to teach myself how to create a program that uses input. I've tried looking at the syntax help file and at page 71 of these lecture slides I found on the internet, but I can't figure out how to do this.
I would appreciate it if you could show me some documentation that covers this specific topic thoroughly. Or just point out what I'm doing wrong below.
As you can see, all I want is to create a short program that checks whether a file exists in the specified folder (capture confirm file), but I want to display my own dialogue box if there is an error (window stopbox note) and if so, then exit the do file in an orderly manner (exit 601).
cap program drop checkfile
program checkfile
syntax varlist, folder(varname) file(varname)
capture confirm file "`folder'/`file'"
if _rc == 601 {
window stopbox note `"`file' is not in `folder'"' // creates a dialogue box for the error
exit 601
}
end
checkfile folder(C:\Users\User\Documents) file(NIDSw5.dta)
Returns the error:
factor-variable and time-series operators not allowed
r(101);
I'm not sure how to use syntax in order to get the folder path and file name. Note that these are usually strings, but I'm guessing that:
"`folder'/`file'"
will result in, for example, ""C:\Users\User\Documents"/"NIDSw5.dta"" if the input is done with quotation marks, so that's why I thought I should use the local(input) method.
Also note that I will use a global variable ($DataIN) instead of putting the folder path string there, and the file name contains a global variable appended onto a string.
Removing varlist, results in the error:
invalid syntax
r(197);

The following works for me:
program checkfile
syntax, folder(string) file(string)
capture confirm file "`folder'/`file'"
if _rc == 601 {
window stopbox note `"`file' is not in `folder'"'
exit 601
}
end
You then simply need to type:
checkfile, folder(C:\Users\User\Documents) file(NIDSw5.dta)
EDIT:
You can also do it without using options as follows:
program checkfile
capture confirm file "`1'/`2'"
if _rc == 601 {
window stopbox note `"`2' is not in `1'"'
exit 601
}
end
checkfile C:\Users\User\Documents NIDSw5.dta

Related

Commands in GWBASIC

I am using GWBASIC and cannot figure out a few things. Like, when I'm saving a program after running it with F4, it says: File not found.
Secondly, when I'm using auto command it shows * with line numbers.
Finally, if I want to take program and its output's print on paper, what should I do?
I am using GWBASIC and cannot figure out a few things. Like, when I'm
saving a program after running it with F4, it says: File not found.
Try saving like this:
SAVE"myprog.bas",a
Secondly, when I'm using auto command it shows * with line numbers.
The star (*) on a line means that line already exists and you are overwriting it.
If you use the command NEW to wipe-out the program from memory before running 'auto', you won't see those stars on lines.
Finally, if I want to take program and its output's print on paper,
what should I do?
1) Save the program as a text file:
SAVE"myprog.bas",a
2) Open the file 'myprog.bas' with a text editor (like Notepad++).
3) Print it.
To print a GW-BASIC program, use the LIST command.
The optional , filename parameter specifies the output for the listing. It could be to a file (e.g. to dump the text so another program can load it), or it could be to a printer device (e.g. LPT1:).
So this should work:
LIST ,LPT1:
See also https://robhagemans.github.io/pcbasic/doc/1.2/#LIST

Scilab compilation "cannot allocate this quantity of memory"

I am facing issues with memory allocation in Scilab after compiling.
I am compiling on a Red Hat on ppc64 (POWER8). Stack limits are already set to unlimited (ulimit -s unlimited). The ./configure script (with several options I am not showing here) runs successfully, but the make all fails and stops. When it stops, it is stuck at the Scilab command prompt with this message:
./bin/scilab-cli -ns -noatomsautoload -f modules/functions/scripts/buildmacros/buildmacros.sce
stacksize(5000000);
!--error 10001
stacksize: Cannot allocate memory.
%s: Cannot allocate this quantity of memory.
at line 27 of exec file called by :
exec('modules/functions/scripts/buildmacros/buildmacros.sce',-1)
-->
I have investigated a bit, and that error message seems to be called of course at line 00027 in buildmatros.sce, where the function stacksize(5000000) is called.
This function is defined in:
scilab-5.5.1/modules/core/sci_gateway/c/sci_stacksize.c
I found a version of the file at this page: http://doxygen.scilab.org/master_wg/d5/dfb/sci__stacksize_8c_source.html.
The condition that is FALSE and that triggers the message seems to me to show up at line 00295.
Inside that file, you see that error is displayed whenever the stacksize given as input is LARGER than what is returned by the method get_max_memory_for_scilab_stack() from the class:
scilab-5.5.1/modules/core/src/c/stackinfo.c
Again I found a version online at the following page:
http://doxygen.scilab.org/master_wg/dd/dfb/stackinfo_8h.html#afbd65a57df45bed9445a7393a4558395
The Method is declared from line 109.
It seems to invoke a variable called MAXLONG, which is however NEVER explicitly declared! As you see, it is declared several times (line 00019, 00035, 00043, 00050), but all lines are commented! [correction: the lines are NOT commented, it was my false understanding of # being a comment sign, but it's not]
So my guess is: MAXLONG is not declared, so the function does not return a value (or it returns 0) and therefore the error message is triggered because the stacksize given as input is higher than 0 or NULL or N/A.
My questions are then:
Why are all lines commented where MAXLONG is defined?
Where does MAXLONG originate from? Is it something passed from the kernel?
How can I solve the problem?
Thanks!
PS - I tried to uncomment the line in buildmacros, and it compiled and installed without issues. However, when I started scilab-cli, it displayed the same message again.
Edit after further investigation:
After further investigation, I found out that what I thought were the comments are indeed instructions for the compiler... but I kept those errors of mine, so that the answer to my question is understandable.
Here are my new points.
In Scilab I noticed that by giving an input stacksize out of bounds, the same method get_max_memory_for_scilab_stack() is invoked, to get the upper bound. The lower bound I've seen it's defined by default.
-->stacksize(1)
!--error 1504
stacksize: Out of bounds value. Not in [180000,268435454].
Also the stacksize used seems fine:
-->stacksize()
ans =
7999994. 332.
However, when trying to give such value an input inbetween, it fails.
-->stacksize(1)
!--error 1504
stacksize: Out of bounds value. Not in [180000,268435454].
It seems to invoke a variable called MAXLONG
It's not a variable, but a pre-processor macro.
Why are all lines commented where MAXLONG is defined?
You should ask that from the person who commented the lines. They're not commented in scilab-5.5.1 that's online.
Where does MAXLONG originate from? Is it something passed from the kernel?
It's defined in the file scilab-5.5.1/modules/core/src/c/stackinfo.c. It's defined to the same value as LONG_MAX which is defined by the standard c library (<limits.h> header). If the macro is not supplied by the standard library, then it's defined to some other, platform specific value.
How can I solve the problem?
If your problem originates from the lack of definition for MAXLONG, then you must define it. One way going about it is to uncomment the lines that define it. Or re-download the original sources since yours don't appear to match with the official ones.

C++: Rename instead of Delete & Copy when using Sync

Currently I have the following part code in my Sync:
...
int index = file.find(remoteDir);
if(index >= 0){
file.erase(index, remoteDir.size());
file.insert(index, localDir);
}
...
// Uses PUT command on the file
Now I want to do the following instead:
If a file is the same as before, except for a rename, don't use the PUT command, but use the Rename command instead
TL;DR: Is there a way to check whether a file is the same as before except for a rename that occurred? So a way to compare both files (with different names) to see if they are the same?
check the md5sum, if it is different then the file is modified.
md5 check sum of a renamed file will remain same. Any change in content of file will give a different value.
I first tried to use Renjith method with md5, but I couldn't get it working (maybe it's because my C++ is for windows instead of Linux, I dunno.)
So instead I wrote my own function that does the following:
First check if the file is the exact same size (if this isn't the case we can just return false for the function instead of continuing).
If the sizes do match, continue checking the file-buffer per BUFFER_SIZE (in my case this is 1024). If the entire buffer of the file matches, return true.
PS: Make sure to close any open streams before returning.. My mistake here was that I had the code to close one stream after the return-statement (so it was never called), and therefore I had errno 13 when trying to rename the file.

Strange output and branch warning when compiling

I compile a fortran 77 code using gfortran and get the following error:
10 open (23,file=outfile,status='old',access='append',err=10)
1
Warning: Branch at (1) may result in an infinite loop
This happens several times.
One of the output files looks like the following:
^L6a10È <90> ) &<9b>LÓLÓLÕ<91><90> <90> <90> È <8e><9b>LÓLÓLÕ<93>2
!MERCURY ¢¤õ/!ô<8a><8a><90> ÿ<90> ÿ<90> ÿÌÖÏ©ü}M<91>
"VENUS «}>±{©±<8b><90> ÿ<90> ÿ<90> ÿʺ93¿<8d>d<91>
However, it should just look like a table of text.
Any ideas?
Your line of code
10 open (23,file=outfile,status='old',access='append',err=10)
specifies that the open statement should transfer control to itself (label 10) in case an error is encountered, so any error could trigger an infinite loop. It also suppresses the output of error messages. If you want to just check for an error status, I would suggest using the iostat and/or iomsg (Fortran 2003) arguments:
open (23, file=outfile, status='old', access='append', iostat=ios, iomsg=str)
Here ios is an integer that will be zero if no errors occur and nonzero otherwise, and str is a character variable that will record the corresponding error message.
The err= argument in your open statement specifies a statement label to branch to should the open fail for some reason. Your code specifies a branch to the line labelled 10 which happens to be the line containing the open statement. This is probably not a good idea; a better idea would be to branch to a line which deals gracefully with an error from the open statement.
The warning from gfortran is spot on.
As to the apparent garbage in your output file, without sight of the code you use to write the garbage (or what you think are pearls perhaps) it's very difficult to diagnose and fix that problem.

Pre-assign parameter in script

Actually I have trouble naming the title of this post. Because I don't know how to summarize my meaning in a professional way. But I'll explain my question as below:
I'm running a program written by C++, command is:
./VariationHunter_SC
Then it'll let you type in many parameters:
Please enter the minimum paired-end insert size:
Please enter the maximum paired-end insert size:
Please enter the pre-processing mapping prune probability:
Please enter the name of the input file:
Please enter the minimum support for a cluster:
Obviously I need to type in such parameters one by one to run the program; But I have thousands of such jobs, and need to pre-assign such parameters in script, and submit script to computer.
So how can I do that?
thx
Edit
so how can I make parameter-list?
Just like below?:
140
160
0
mrfast.vh
1
Seems the program cannot recognize these numbers, and distribute numbers..
This depends on how the program actually reads the data that you type in - it's likely that its reading stdin, so you could use separate files with the parameters and pass them in via redirection: ./VariationHunter_SC < parameter-file
It's also possible that the program will accept parameters on the command line, but there's no way of really knowing that (or how) except by whatever documentation the program might come with (or by reading the source code, if it's available and there is no other accurate docs).
Simply use the piping character to pipe the contents of a file to your program
example, in a windows command shell:
echo "asdf" | pause
This will pass "asdf" to the pause program. As a result, pause will print a "Press any key to continue" message, then imediately continue because it will receive the "asdf" string as a response.
So, overall, write or use a program that outputs the contents of your file. Call it, then pipe its output to the program that needs the input.
The unix cat command is such a command that writes the contents of a file to output, or to the input of another executable if you are piping the output.