I am considering learning a new programming language.
I am a It person with both hardware and software knowledge. May day to day
job is a LAN Administrator. I.E. installing networks, servers, pc's installing
software, running backups and occasionally writing a quick program.
I usually through together quick programs in Borland C. As this is what I have
been using for one program a year. (I only spend a couple of hundred hours
a year programming)
1.First language Basic on a number of machines. TRS-80,System 80,Applesoft etc.
2.Looked at Pascal. Did not realy get into it.
3.Read a book on LISP .. could not get my head around it.
4.Enjoyed learning Prolog. Ran Endburrogh Prolog on Vax.
5.Learnt and used Turbo C and Borland C. Most experience on these compilers
6.HTML on Notepad, Homesite etc.
Machine Language.
1. Z-80.. #23 inc HL. #c3 Jump, #cd call ...Cheers to Craig Amey. HomeBuilt Z-80 from scratch
2. M680XX I like these CPUs
3. 80x86 ..TSR routines and patches to code. Cheers to Sourcer (V-Comms)
Which language I should learn?
My wish list:
* The language should be available for both Windows and GNU/Linux.
* The language should be advanced enough to build complex programs for GUI
apps, graphical visualization and what not (ie. have a Resouce editor at least)
* Easy to pick up once per year.
* The language should have a future - I want to use it for the next 10 years.
* The language should be able to read directories ..(ie findfirst...Findnext)
* Easy string handling, and varible arrays ..(C99 does not have runtime varible
arrays.)(I.e. automated memory handling. garbage removal)
I am looking at maybe Python or C# now that mono exits . C++ looks to complex to
use only once a year.
My next project is to put a window front end on various c programs.
example code
Any comments are welcome on sugested languages and good programing books.
Even on Borland C (C++).
Cheers All
James P.
<code>
* File = F:\RIS\super\JLP\TC\EMTPYDIR1.C
* Under = Software
* Date = 1/1/2007
* Update= 1/4/2007
* Vers = 4.0
*
* James P*******'s DIRerctory Empty Program
* Version 4.0
* Hardcoded BAT & Log output
*
* This program outputs a directory list with number and size of files
* It also deletes all empty directories for Floppy, Hard Disks
* Updated for 98se,NT,2000,and XP
*
* Usage:
*
* EMPTYDIR [options] [outputfile]
*
* Future options
* /H -- HTML Output
* /k -- Actually remove files
* /t -- Kilobytes
* /T -- Thousands of Bytes
* /V -- Version output
*/
#include <dir.h>
#include <dos.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "getopt.h"
/*
* Defined types
*
*/
typedef enum {FALSE,TRUE} BOOLEAN;
typedef enum {GOOD,BAD} RCODE;
typedef struct ffblk FFBLK;
/*
* Prototypes
*/
long dir_size(void);
long dir_space(void);
void files(int level);
void line(int level);
RCODE firstdir(char *pathname,FFBLK *dirblk);
RCODE nextdir(FFBLK *dirblk);
int nextlevel(RCODE done,FFBLK *dirblk,FFBLK *tempblk);
int processargs(int argc, char **argv);
void usage(void);
/*
* External varibles in optarg.h
*/
extern char *optarg;
extern int optind;
/*
* Globals
*/
int level,dirnum,tdeleted,tempty,tfiles,tspace,tsize;
BOOLEAN csv,debugme,html,fileout,kill,thousands;
FILE *fhdir; // These file handles are for HTML output files
FILE *fhlog; // These file handles are for Log output files
FILE *fhbat; // These file handles are for Batch output files
char buf[100],graph[20];
char progname[80]="Emptydir";
char ver[10]="Beta 4.0";
int main(int argc, char **argv)
{FFBLK dirblk,tempblk;
char buf[100],path[MAXDIR];
char filehtml[20];
int son;
RCODE done;
debugme=FALSE;
fileout=FALSE;
kill=FALSE;
html=TRUE;
thousands=FALSE;
dirnum=0;
level=0;
tdeleted=0;
tempty=0;
tspace=0;
tsize=0;
getcwd(buf,100);
printf("James P*****s Empty Directory %s.\n",ver);
printf("\%s directory's subdirectorys.\n",buf);
processargs(argc,argv);
if(html)
{strcpy(filehtml,"emptydir.log");
printf("filehtml=%s",filehtml);
if((fhlog= fopen(filehtml,"w+b"))!=NULL)
{fprintf(fhlog,"Empty Directory Log file version=%s\r\n",ver);
fprintf(fhlog,"===================================\r\n");
fprintf(stdout,"file %s is open\n",filehtml);
}
else
{printf("file %s has failed to open\n",filehtml);
abort();
}
strcpy(filehtml,"EmptyDirs.HTM");
if((fhdir= fopen(filehtml,"w+b"))!=NULL)
{fprintf(fhdir,"<Head><meta name=\"generator\" content=\"JPDIR-%s\">\r\n",ver);
fprintf(fhdir,"<LINK REL=\"stylesheet\" TYPE=\"text/css\" HREF=\"jpdir.css\">");
printf("file %s is open\n",filehtml);
}
else
{printf("file %s has failed to open\n",filehtml);
abort();
}
strcpy(filehtml,"EmptyDirs.Bat");
if((fhbat= fopen(filehtml,"w+b"))!=NULL)
{fprintf(fhbat,"Echo Are you sure you want to delete empty directories\n");
fprintf(fhbat,"pause\n");
printf("file %s is open\n",filehtml);
}
else
{printf("file %s has failed to open\n",filehtml);
abort();
}
}
if (html)
{fprintf(fhdir ,"<title>JDIR</title></head>\r\n <Body>");
fprintf(fhdir ,"<H1>\%-12s directory's subdirectorys & files</H1><Table CELLSPACING=0>");
}
fprintf(fhlog,"DirNum,Level,Path,DSize\n");
if (debugme){ printf("Buffer = %s\n",buf);}
done=getcurdir(0,path);
if (debugme) {printf("path = %s\n",path);}
if(done)
{printf("Directory error");
abort();
}
if (fileout) files(-1);
tspace=dir_space();
tsize=dir_size();
printf("root files=%ld space=%ld\n",tsize,tspace);
// now do directory(ies)
done=firstdir("*",&dirblk);
firstdir("*",&tempblk);
while (!done)
{if (debugme) printf("About to change to %ld--%s\n",level,dirblk.ff_name);
chdir(dirblk.ff_name);
dirnum++;
if (debugme) printf("about to run nextlevel\n");
son=nextlevel(done,&dirblk,&tempblk);
tsize+=son;
if (debugme) printf("back from nextlevel\n");
chdir("..");
//==
if (son==0)
{fprintf(fhlog,"=delete");
fprintf(fhdir,"=delete");
fprintf(fhlog,"\r\nRmdir %s\r\n",dirblk.ff_name);
fprintf(fhbat,"\r\nRmdir %s",dirblk.ff_name);
if (kill)
{tdeleted++;
printf("Delete %s\n",dirblk.ff_name);
rmdir(dirblk.ff_name);
}
tempty++;
}
//==
done=nextdir(&dirblk);
}
if(html){fprintf(fhdir,"<tr>%s has found %ld files, %ld space in %ld Directories\n",progname,tsize,tspace,dirnum);
fprintf(fhdir,"<tr>%s has found %ld Empty Directories, Deleted %ld Directories\n",progname,tempty,tdeleted);
fprintf(fhdir ,"</Table><H1>End of file</H1></Body><HTML>");
printf("about to close HTML file\n");fclose(fhdir);;
}
// progname = *argv;
printf("%s has found %ld files, %ld space in %ld Directories\n",progname,tsize,tspace,dirnum);
printf("%s has found %ld Empty Directories, Deleted %ld Directories\n",progname,tempty,tdeleted);
fprintf(fhlog,"%s has found %ld files, %ld space in %ld Directories\n",progname,tsize,tspace,dirnum);
fprintf(fhlog,"%s has found %ld Empty Directories, Deleted %ld Directories\n",progname,tempty,tdeleted);
printf("about to close log file\n");fclose(fhlog);;
printf("about to close Bat file\n");fclose(fhbat);;
return 0;
}
void line(int level)
{int i;
for (i=0;i<level;i++)
{printf("%c ",graph);
if (html)
{if (graph==' ')
{fprintf(fhdir," ");
}
else
{fprintf(fhdir,"│");
}
}
}
}
/*
* Firstdir
* Finds first directory that is not . or ..
*
* Returns Good if directory found
*/
RCODE firstdir(char *pathname,FFBLK *dirblk)
{RCODE done;
done=findfirst(pathname,dirblk,FA_DIREC);
while(!done)
{if (dirblk->ff_attrib != FA_DIREC)
{if (debugme) printf("%s is not a dirctory\n",dirblk->ff_name);
}
else {if (dirblk->ff_name[0]=='.')
{if (debugme) printf("found %s\n",dirblk->ff_name);
}
else {if (debugme) printf("done on ffname=%s\n",dirblk->ff_name);
done=GOOD;
return done;
}
}
done=findnext(dirblk);
}
done=BAD;
return done;
}
/*
* nextdir
* Finds Next directory that is not . or ..
*
* Returns Good if directory found
*/
RCODE nextdir(FFBLK *dirblk)
{RCODE done;
done=findnext(dirblk);
while(!done)
{if (dirblk->ff_attrib != FA_DIREC)
{if (debugme) printf("%s is not a dirctory\n",dirblk->ff_name);
}
else {if (dirblk->ff_name[0]=='.')
{if (debugme) printf("found %s\n",dirblk->ff_name);
}
else {if (debugme) printf("done on ffname=%s\n",dirblk->ff_name);
done=GOOD;
return done;
}
}
done=findnext(dirblk);
}
done=BAD;
return done;
}
long dir_space()
{RCODE done;
long space;
FFBLK ffblk;
space=0;
done=findfirst("*.*",&ffblk,FA_SYSTEM|FA_HIDDEN);
while (!done)
{space+=ffblk.ff_fsize;
done=findnext(&ffblk);
}
return(space);
}
long dir_size()
{RCODE done;
long size;
FFBLK ffblk;
size=0;
done=findfirst("*.*",&ffblk,FA_SYSTEM|FA_HIDDEN);
while (!done)
{size++;
done=findnext(&ffblk);
}
return(size);
}
int nextlevel(RCODE done,FFBLK *dirblk,FFBLK *tempblk)
{FFBLK dirnew,dirnew2;
long size,space,son;
size=0;
son=0;
space=0;
if (fileout) files(-1);
if (html)
{fprintf(fhdir,"<TR><TD><TT>");
}
line(level);
if(nextdir(tempblk))
{printf("\xC0\xc4");
if (html)
{fprintf(fhdir ,"└─</TT>");
fprintf(fhdir ,"%s",dirblk->ff_name);
}
graph[level]=' ';
}
else {printf("\xC3\xc4");
if (html)
{fprintf(fhdir ,"├─</TT>");
fprintf(fhdir ,"%s",dirblk->ff_name);
}
graph[level]='\xB3';
}
printf("sub %s",dirblk->ff_name);
space=dir_space();
size=dir_size();
printf("\t\tfiles=%ld space=%ld\n",size,space);
fprintf(fhlog ,"\n%d,%d,%s,%ld,%ld",dirnum,level,dirblk->ff_name,size,space);
// now do directory(ies)
done=firstdir("*",&dirnew);
firstdir("*",&dirnew2);
while (!done)
{if (debugme) printf("About to change to %ld--%s\n",level,dirnew.ff_name);
chdir(dirnew.ff_name);
dirnum++;
level++;
son=nextlevel(done,&dirnew,&dirnew2);
size+=son;
getcwd(buf,100);
chdir("..");
//==
if (son==0)
{fprintf(fhlog,"=delete");
fprintf(fhdir,"=delete");
fprintf(fhbat,"\r\nRmdir \"%s\"",buf);
fprintf(fhbat,"\r\nRmdir %s",dirnew.ff_name);
if (kill)
{tdeleted++;
printf("Delete %s\n",dirnew.ff_name);
fprintf(fhlog,"\nDelete %s",dirnew.ff_name);
fprintf(fhlog,"\r\nRmdir %s\r\n",dirnew.ff_name);
if (rmdir(dirnew.ff_name))
{printf("\nCan not delete %s and error=%d",dirnew.ff_name,errno);
perror("error");
}
}
tempty++;
}
//==
level--;
done=nextdir(&dirnew);
}
getcwd(buf,100);
fprintf(fhlog ,"\n=%d,%d,%s,%ld,%ld",dirnum,level,buf,son,size);
return(size);
}
int processargs(int argc, char **argv)
{
int opt, rc = 0;
BOOLEAN file = FALSE;
// progname = *argv;
strcpy(progname,argv[0]);
printf("progname =%s",progname);
while ((opt = pgp_getopt(argc, argv, "bfhktT?")) != EOF)
{printf("opt=%c",opt);
switch (opt)
{case 'b': debugme=TRUE;printf("b used\n"); break;
case 'f': file =TRUE; printf("f used\n"); break;
case 'k': kill=TRUE; break;
case 'r': kill=TRUE; break;
case 't': thousands=TRUE; break;
case 'T': thousands=FALSE; break;
default: usage();
}
}
return rc;
}
void files(level)
{int i;
RCODE done;
FFBLK ffblk;
char shorty[13];
// dirnum++;
done=findfirst("*.*",&ffblk,0);
if (!done)
{if(html)
{for (i=0;i<level;i++)
{if (graph==' ')
{fprintf(fhdir,"│");
}
else
{fprintf(fhdir,"│");
}
}
}
}
while (!done)
{line(level+2);
tfiles++;
GetShortPathName(ffblk.ff_name,shorty,13);
printf("%12s",shorty);
printf("\t%8ld",ffblk.ff_fsize);
printf("\t%s\n",ffblk.ff_name);
done=findnext(&ffblk);
}
dirnum++;
}
void usage(void)
{
fprintf(stderr, "usage: EmptyDir %s [-bfhkmtvw] [-f [file]] \n",ver);
fprintf(stderr, "Deletes files based on date, time, size, Version or MD5 Message Digests\n");
fprintf(stderr, " -b Debug output (Verbose mode!) (default is no Debug)\n");
fprintf(stderr, " -d Database output (Verbose mode!) (No Database output yet!\n");
fprintf(stderr, " -f Files in ouput (default is files.csv)\n");
fprintf(stderr, " -h No HTML output (default is HTML Output\n");
fprintf(stderr, " -k Kill empty Directories (default is Not to Remove Directories)\n");
fprintf(stderr, " -r Remove empty Directories (default is Not to Remove Directories)\n");
fprintf(stderr, " -t Thousands of Bytes (default is Bytes)\n");
fprintf(stderr, " -T KiloBytes (default is Bytes)\n");
fprintf(stderr, " Future options\n");
fprintf(stderr, " -d Database output\n");
exit(2);
}
</code>