How does F# Interactive #I command know about project path? - visual-studio

Here is the scenario:
Open Visual Studio. This was done in VS2010 Pro.
Open F# Interactive within Visual Studio
Open project with fsx file
Note: Project and fsx file are in E:\<directories>\fsharp-tapl\arith
Send commands to F# Interactive from fsx file
> System.Environment.CurrentDirectory;;
val it : string = "C:\Users\Eric\AppData\Local\Temp"
I was not expecting a Temp directory but it makes sense.
> #r #"arith.exe"
Examples.fsx(7,1): error FS0082: Could not resolve this reference.
Could not locate the assembly "arith.exe".
Check to make sure the assembly exists on disk.
If this reference is required by your code, you may get compilation errors.
(Code=MSB3245)
Examples.fsx(7,1): error FS0084: Assembly reference 'arith.exe' was not found
or is invalid
The #r command error shows that F# Interactive currently does not know the location of arith.exe.
> #I #"bin\Debug"
--> Added 'E:\<directories>\fsharp-tapl\arith\bin\Debug'
to library include path
So we tell F# Interactive the location of the arith.exe.
Notice that the path is NOT an absolute path but a sub-path of the project.
I have not told F# Interactive the location of the arith project
E:\<directories>\fsharp-tapl\arith
> #r #"arith.exe"
--> Referenced 'E:\<directories>\fsharp-tapl\arith\bin\Debug\arith.exe'
And F# Interactive correctly finds arith.exe reporting the correct absolute path.
> open Main
> eval "true;" ;;
true
val it : unit = ()
This confirms that arith.exe was correctly found, loaded and works.
So how did F# Interactive #I command know the project path since the current directory is of no help?
What I am really after is from within F# Interactive how does one get the path to the project, E:\<directories>\fsharp-tapl\arith.
EDIT
> printfn __SOURCE_DIRECTORY__;;
E:\<directories>\fsharp-tapl\arith
val it : unit = ()

In F# Interactive, the default directory to search is the source directory. You can query it easily using __SOURCE_DIRECTORY__.
This behaviour is very convenient to allow you to use relative paths. You often have fsx files in the same folder with fs files.
#load "Ast.fs"
#load "Core.fs"
When your refer to a relative path, F# Interactive will always use the implicit source directory as the starting point.
#I ".."
#r ... // Reference some dll in parent folder of source directory
#I ".."
#r ... // Reference some dll in that folder again
If you want to remember the old directory for next reference, you should use #cd instead:
#cd "bin"
#r ... // Reference some dll in bin
#cd "Debug"
#r ... // Reference some dll in bin/Debug

Related

Unable to load/require file from Lua running from Atom in Windows

I'm trying to use Atom to run a Lua script. However, when I try to load files via the require() command, it always says it's unable to locate them. The files are all in the same folder. For example, to load utils.lua I have tried
require 'utils'
require 'utils.lua'
require 'D:\Users\Mike\Dropbox\Lua Modeling\utils.lua'
require 'D:\\Users\\Mike\\Dropbox\\Lua Modeling\\utils.lua'
require 'D:/Users/Mike/Dropbox/Lua Modeling/utils.lua'
I get errors like
Lua: D:\Users\Mike\Dropbox\Lua Modeling\main.lua:12: module 'D:\Users\Mike\Dropbox\Lua Modeling\utils.lua' not found:
no field package.preload['D:\Users\Mike\Dropbox\Lua Modeling\utils.lua']
no file '.\D:\Users\Mike\Dropbox\Lua Modeling\utils\lua.lua'
no file 'D:\Program Files (x86)\Lua\5.1\lua\D:\Users\Mike\Dropbox\Lua Modeling\utils\lua.lua'
no file 'D:\Program Files (x86)\Lua\5.1\lua\D:\Users\Mike\Dropbox\Lua Modeling\utils\lua\init.lua'
no file 'D:\Program Files (x86)\Lua\5.1\D:\Users\Mike\Dropbox\Lua Modeling\utils\lua.lua'
The messages says on the first line that 'D:\Users\Mike\Dropbox\Lua Modeling\utils.lua' was not found, even though that is the full path of the file. What am I doing wrong?
Thanks.
The short answer
You should be able to load utils.lua by using the following code:
require("utils")
And by starting your program from the directory that utils.lua is in:
cd "D:\Users\Mike\Dropbox\Lua Modeling"
lua main.lua
The long answer
To understand what is going wrong here, it is helpful to know a little bit about how require works. The first thing that require does is to search for the module in the module path. From Programming in Lua chapter 8.1:
The path used by require is a little different from typical paths. Most programs use paths as a list of directories wherein to search for a given file. However, ANSI C (the abstract platform where Lua runs) does not have the concept of directories. Therefore, the path used by require is a list of patterns, each of them specifying an alternative way to transform a virtual file name (the argument to require) into a real file name. More specifically, each component in the path is a file name containing optional interrogation marks. For each component, require replaces each ? by the virtual file name and checks whether there is a file with that name; if not, it goes to the next component. The components in a path are separated by semicolons (a character seldom used for file names in most operating systems). For instance, if the path is
?;?.lua;c:\windows\?;/usr/local/lua/?/?.lua
then the call require"lili" will try to open the following files:
lili
lili.lua
c:\windows\lili
/usr/local/lua/lili/lili.lua
Judging from your error message, your Lua path seems to be the following:
.\?.lua;D:\Program Files (x86)\Lua\5.1\lua\?.lua;D:\Program Files (x86)\Lua\5.1\lua\?\init.lua;D:\Program Files (x86)\Lua\5.1\?.lua
To make that easier to read, here are each the patterns separated by line breaks:
.\?.lua
D:\Program Files (x86)\Lua\5.1\lua\?.lua
D:\Program Files (x86)\Lua\5.1\lua\?\init.lua
D:\Program Files (x86)\Lua\5.1\?.lua
From this list you can see that when calling require
Lua fills in the .lua extension for you
Lua fills in the rest of the file path for you
In other words, you should just specify the module name, like this:
require("utils")
Now, Lua also needs to know where the utils.lua file is. The easiest way is to run your program from the D:\Users\Mike\Dropbox\Lua Modeling folder. This means that when you run require("utils"), Lua will expand the first pattern .\?.lua into .\utils.lua, and when it checks that path it will find the utils.lua file in the current directory.
In other words, running your program like this should work:
cd "D:\Users\Mike\Dropbox\Lua Modeling"
lua main.lua
An alternative
If you can't (or don't want to) change your working directory to run the program, you can use the LUA_PATH environment variable to add new patterns to the path that require uses to search for modules.
set LUA_PATH=D:\Users\Mike\Dropbox\Lua Modeling\?.lua;%LUA_PATH%;
lua "D:\Users\Mike\Dropbox\Lua Modeling\main.lua"
There is a slight trick to this. If the LUA_PATH environment variable already exists, then this will add your project's folder to the start of it. If LUA_PATH doesn't exist, this will add ;; to the end, which Lua fills in with the default path.

Including 'Run Script' phase output files in build

In Xcode 7, you can create 'Run Script' phases in the Build Phases tab. At the bottom of the area, there's an 'Input Files' section and an 'Output Files' section.
I have a script that generates a .cpp file at $(DERIVED_FILE_DIR)/myfile.cpp. The file is listed in the 'Output Files' section of the phase. However, it appears that it's not compiled into my program, as the symbol that it defines are identified as missing by the linker.
How can I tell Xcode to compile this file as well?
One possible solution (which feels like a hack) is to insert the built file into the project, set its location (in the Identity and Type section of the Utilities bar) and then edit its location in the project file with a text editor for computer independence. In my case, the file entry (with newlines for readability) now looks like:
DC40C4121C7FC98F0087702A /* bindings.cpp */ = {
isa = PBXFileReference;
lastKnownFileType = sourcecode.cpp.cpp;
name = myfile.cpp;
path = "$(DERIVED_FILE_DIR)/myfile.cpp";
sourceTree = "<absolute>";
};
This is interpreted by the file browser as a file whose absolute path is literally $(DERIVED_FILE_DIR)/myfile.cpp (and the file always shows in red in the project explorer), but the build system will grab the file from the correct location.

Can Visual Studio read a set of include file paths from a text file for the Additional Include Directories?

I'm trying to figure out how to get Visual Studio to read a set of include files from a text file.
For example, I would like to create a text file called IncludePaths.txt that contains a list of include paths such as "/I ../../header"
I would then tell Visual Studio reference this file.
I believe you could do this by adding #IncludePaths.txt to the Additional Include Directory, but I cannot get this to work. I have seen this done in projects I have worked on in the past but I can't find any documentation or figure out the trick.
After a little more research and talking to a couple of other developers, I figured out the "trick"
1) Create a file called IncludePaths.txt next to my project file.
2) Add your include paths to this file...
/I "..\..\..\..\open\common\include"
/I "..\..\..\common\include"
/I "..\..\"
3) Go to Properties -> C++ -> Command Line
4) Under "Additional Options" add #IncludePaths.txt
Alternatively, you can use custom properties to get this to work too.

Trying to open a file in C++, but the file cannot be found

I have an algorithm in C++ (main.cpp) and I use CLion to compile and run it. Algorithm would read strings from text file, but there is a mistake:
Could not open data.txt (file exists and placed in one folder with main.cpp)
How can I fix it and make this file "visible" to CLion?
If you are using fopen or something similar and just passing "data.txt", it is assumed that that file is in the current working directory of the running program (the one you just compiled).
So, either
Give a full path instead, like fopen("/full/path/to/data.txt"), where you use the actual full path
(not preferable), Move data.txt to the directory where CLion runs its compiled programs from.
(for #2, here's a hacky way to get that directory)
char buf[1024]; // hack, but fine for this
printf("%s\n", getcwd(buf, 1024));
Run/Edit configurations...
Select your application (on the lefthandside of the window)
Specify Working directory
Apply
Now you can fopen relatively from working directory.
I found another way to solve this problem.
#Lou Franco's solution may affect the project structure. For example, if I deploy code on a server, I should move the resource file to specific directory.
What I do is modify the CmakeLists.txt, on Windows, using
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "D:\\science\\code\\English-Prediction")
CMAKE_RUNTIME_OUTPUT_DIRECTORY is a CMake variable, it assigns the work directory of CLion work directory.
Continuing with the CMAKE_RUNTIME_OUTPUT_DIRECTORY CMakeLists variables, I do the following. In the root directory of my project, I create a directory, e.g., out. Then, in my CMakeLists.txt I set the CMAKE_RUNTIME_OUTPUT_DIRECTORY to that directory:
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${PROJECT_SOURCE_DIR}/out)
Note, that must come before you have
add_executable(YourProject ${SOURCE_FILES})
I might also add that instead of using fopen() I would keep it more object-oriented by using std::ifstream:
std::ifstream inFile("data.txt");
// check if it opened without issue...
if (!inFile) {
processError(); // a user-defined function to deal with the issue
} else {
// All is good, carry on...
// and when you're done don't forget
inFile.close();
}

Include File that is not in the same directory as script

I have a NSIS script that is attempting to include a .NSI file that sits in a different folder.
My Problem: When I go to compile my script I get the compile error !include: could not find: "../Utilities.nsi". This file exists and is in the correct location I am specifying(in the parent directory - one step back).
How can I include a file that sits in another directory? I hope its possible.
!include "../Utilities.nsi" # include error: '!include: could not find: "../Utilities.nsi"'
InstallDir "abc"
Name "def"
OutFile "def.exe"
Section
DetailPrint "Hello World"
SectionEnd
The manual says this about !include:
This command will include 'file' as if it was part of the original
script. Note that if a file is included in another directory, the
current directory is still where the script was compiled from (not
where the included file resides). If the compiler can't find the file
it will look for it in every include directory. See !addincludedir for
more information. If the /nonfatal switch is used and no files are
found, a warning will be issued instead of an error."
Also, the examples in the manual do not use quotation marks -- did you try
removing them? Also, "/" => "\".

Resources