Loading/Modifying/Saving Changes to Text File - haskell

Allow me to start by sharing what I have so far:
main :: IO ()
main = do contents <- readFile "filmList.txt"
let database = (read contents :: [Film])
putStr "Please enter your username: "
userName <- getLine
menu database
where menu newDb = do putStrLn "\nPlease select an option:"
putStrLn "1: Display all films currently in the database"
putStrLn "2: Add a new film to the database (and display all films)"
putStrLn "3: "
putStrLn "4: Save Database"
putStrLn "5: Exit"
putStr "\nSelected option: "
option <- getLine
case option of "1" -> putStrLn(displayFilms newDb)
"2" -> do putStr "Name of film: "
title <- getLine
putStr "Name of director: "
director <- getLine
putStr "Year of release: "
year <- getLine
putStrLn(displayFilms (addNewFilm title director (read year) newDb))
menu newDb
`
I have managed to load a txt file with the database of Film types but I cannot figure out how to go about actually making changes to the data. When I try to run option 2, I get a list of all the films with the newly added one as well but if I then run option 1 to list all films, it doesn't include the newly added film. Should I be saving back to the txt file each time a new Film instance is added? Any help is greatly appreciated, thank you!

Keep in mind that everything in Haskell is immutable. When you write addNewFilm (addNewFilm title director (read year) newDb, that doesn't change the database represented by newDb to include the new information; it merely returns a new database that has all the old information plus the new row. It's your responsibility to choose where and when to use the old database (named, ironically, newDb) or the new one returned by the function.
For example, you might write this case instead:
case option of "1" -> putStrLn (displayFilms newDb) >> menu newDb
"2" -> do ...
let evenMoreReallyNewDb = addNewFilm title director (read year) newDb
putStrLn (displayFilms evenMoreReallyNewDb)
menu evenMoreReallyNewDb
You might notice that both cases end with a very similar pattern (a putStrLn . displayFilms and then a menu). Unifying them would be a good idea; see if you can see how to do that yourself.
If you want to write the modified database back to the file, you will of course need to do that explicitly using writeFile or a similar function.

Related

How do I embed formatted R code in table cells in rmarkdown?

I am working on a vignette for an R package where I want to show how to do the same thing in two R packages. My preferred approach would be to include several tables, where I can show the appropriate code next to each other, something like so:
I don't care about the exact fonts, but I would like to see the R code laid out nicely and clearly, like it would be in a regular rmarkdown chunk, but then in a cell of a table.
Is there a way to achieve something like this in rmarkdown?
(I imagine it can by done by typing html directly, but that would be very cumbersome because I don't know html very well.)
If I understand your question correctly, you just want the R code to be able to be displayed in Rmarkdown?
`r ''````{r}
setup <- pacakge2::gogo(x) %>%
dplyr::filter(blabla2)
packages2::plot(setup)
```
This allows you to show your code in an R chunk
If you want to show your entire code you could do this
````markdown
`r ''````{r}
steup <- pacakge2::gogo(x) %>%
dplyr::filter(blabla2)
packages::plot(setup)
```
````
Which actually renders your r code as markdown code
How to do it with my huxtable package. You'll need at least version 5.0.
library(huxtable)
hx <- huxtable(
c("", "Goal A", "Goal B", "Goal C"),
c("Package 1", "", "", ""),
c("Package 2", "", "", "")
)
hx[2, 2] <- "`setup <- package1::start_run()`"
markdown(hx)[2, 2] <- TRUE
quick_pdf(hx)
Result:

gWidgets gfile: Directing User to a folder in the browser pop-up

I'm creating a GUI with R and I want to improve the gfile directory selector.
I'm trying to add an argument so that, when the browse window appears, it has preselected a part of the path.
I.e.
when
select.button <- gbutton("Select", container=win, handler = function(h,...) {
selection <- gfile(type = c ("selectdir"))
})
is activated I want the pop-up to show subfolders in a particular folder(frex the desktop).
I think that the filter argument is what I need(as per the manual cited below), but I can't quite make it work.
filter
Filter for files shown during selection. Can be nested list, as in example or a
named character vector with the names a description and value a file extension
(no dots) of files endings to match.
I've also tried initial.dir with the following combinations:
selection <- gfile(type = c ("selectdir"), initial.dir="/home/robert")
selection <- gfile(type = c ("selectdir"), initial.dir="/home/robert/")
selection <- gfile(type = c ("selectdir"), initial.dir="/home/robert/R/")
selection <- gfile(type = c ("selectdir"), initial.dir="home/robert/R/")
selection <- gfile(type = c ("selectdir"), initial.dir=(/home/robert/R/))

How to properly link DCL to AutoLisp?

I'm trying to build a very basic AutoLisp interface. I'm a total beginner at this, so after failing to code this from scratch, I turned to studying DCL properly. I followed this tutorial:
http://www.afralisp.net/dialog-control-language/tutorials/dialog-boxes-and-autolisp-part-1.php
And I got the same error. AutoCAD basically exits from executing the function, as if the dcl file wasn't even there.
I tried typing the address completely into it, but I think it should be able to work simply like linking HTML to images found in the same folder.
Below you have my code:
DCL:
samp1 : dialog {
label = "Structural Holes";
ok_cancel;
}
Lisp:
(defun C:samp1()
(setq dcl_id (load_dialog "samp1.dcl"))
(if (not (new_dialog "samp1" dcl_id))
(exit)
)
(action_tile
"cancel"
"(done_dialog)(setq userclick nil)"
)
(action_tile
"accept"
"(done_dialog)(setq userclick T))"
)
(start_dialog)
(unload_dialog dcl_id)
(princ)
)
(princ)
Thanks to anyone who will take the time to help me out with this. I'm starting to be quite desperate and it's my first and only autolisp project, so I have no experience whatsoever...
LE: Please note that the dcl file and the lisp file are both found in the same folder, no other subfolders or anything else.
Could not find **.DCL file
error: quit / exit abort
error: LOAD failed
This usually means the autolisp file or DCL file could not be found. To solve this problem, make sure you put your autolisp and DCL files inside the AutoCAD search path. To be more specific, put them in a directory that is part of your "Support File and Search Path". To find the AutoCAD support file and search path list, do the following:
In AutoCAD, click on the TOOLS drop down menu.
Go to the OPTIONS menu item.
Click on the FILES tab.
Click on the plus sign + in front of SUPPORT FILE AND SEARCH PATH.
This is your search path location. The directories listed there are searched in order, from top to bottom for any autolisp program you try to load. It is also used to find blocks and DCL files.
Either add the directory you store your autolisp and DCL files, or move your autolisp and DCL files into one of the directories listed here. This should end the errors listed above.
I came across this piece of information by accident here:
http://www.jefferypsanders.com/autolisp_nodcl.html
HUGE THANKS to JefferyPSanders for that......
For what its worth, you can also create a dialog on the fly in a "known directory" (like the directory AutoCAD resides in for example). The following will demonstrate that.
(defun _make-getstring-dialog-on-the-fly ( / fn f dcl dcl_id userclick str)
(setq fn (strcat
(vl-filename-directory
(findfile "acad.exe")) "\\$vld$.dcl")
f (open fn "w")
dcl
'(
"stringdlg : dialog {"
"label = \"Charater Array\";"
": edit_box {"
"label = \">>:\";"
"edit_width = 20;"
"key = \"stringdlg\";"
"is_default = true;"
"}"
": row {"
"alignment = centered;"
"fixed_width = true;"
" : button {"
" label = \"OK\";"
" key = \"dcl_accept\";"
" width = 10;"
" allow_accept = true;"
" }"
"}"
"}"
)
)
(mapcar
(function
(lambda ( x )
(write-line x f)
(write-line "\n" f)))
dcl)
(close f)
(setq dcl_id (load_dialog fn))
(new_dialog "stringdlg" dcl_id)
(action_tile "stringdlg" "(setq str $value)(done_dialog)")
(setq userclick (start_dialog))
(unload_dialog dcl_id)
str
)

VBScript not working? Page setup wrong

I have an Excel report program. When it prints, I want the date to be on the left.
I used this code
.LeftHeader = "Printed on &D &T"
However, I need to put a comment above in the "head" comment.
head = "In these quotes should be the date"
What should be in the quotes to print the date?
The following gives date as formatted string . You can modify it to suit your requirements
head = Format(Date(), "yyyy/mm/dd")

haskell cgi web programming help

I have a form:
<div id="form">
<form action="upload.cgi" method="get" enctype="multipart/form-data">
<input type="file" name="file" id="file"/>
<input type="submit" value="Upload"/>
</form>
</div>
and the upload.cgi is:
saveFile n =
do cont <- liftM fromJust $ getInputFPS "file"
let f = uploadDir ++ "/" ++ basename n
liftIO $ writeFile f cont
return $ paragraph << ("Saved")
uploadDir = "./uploadDirectory"
basename = reverse . takeWhile (`notElem` "/\\") . reverse
page t b = header << thetitle << t +++ body << b
myFromJust (Just a) = a
myFromJust Nothing = "gs"
cgiMain = do
mn <- getInputFilename "file"
h <- saveFile (myFromJust mn)
output . renderHtml $ page "Saved" h
main = runCGI $ handleErrors cgiMain
The problem is that every time I try to upload a file instead of saving that file, a file called gs is made(from myFromJust function, if I use fromJust I get Nothing and the program fails) whose contents is the uploaded file name.
So, I try to upload a file called something.zip and i get a file called gs whose contents is something.zip (written as text).
I think the problem is that the getInputFilename "file" or getInputFPS don't return anything but I dont't know why.
Is something wrong with the form or the program?
The problem is that the original code1 uses POST; but in the HTML Form of the question, HTML GET is used instead. The fix is to change GET to POST in the HTML.
From the original example where it uses HTTP POST:
fileForm =
form ! [method "post"
, enctype "multipart/form-data"]
<< [afile "file", submit "" "Upload"]
The new Form (partly below) where it improperly uses GET.
<form action="upload.cgi"
method="get" enctype="multipart/form-data">
Notes
1 See Section 9: Web/Literature/Practical web programming in Haskel

Resources