Saturday, October 10, 2009

Dbase utility prog comparing AgingBase.dbf with AgingBaseWKS.dbf for Tagaytay Highlands

#include
clear

//20091010 - GMR!
//Tagaytay Highlands
// this program is a utility to check/compare values of AgingBase.dbf with AgingBaseWKS.dbf

/*
Example:
    AgingBase.dbf                 
      MemAcctID        TranDate        Amount
      50                    08/31/2009    1000.00
      50                    06/30/2009    1500.00
      50                    05/31/2009     100.00
      75                    08/31/2009    2000.00
      75                    07/31/2009     300.00
      75                    06/30/2009     100.00
      75                    05/31/2009    2300.00
      75                    04/30/2009    3000.00
      75                    03/31/2009    1000.00

   AgingBaseWKS.dbf

       MemAcctID        Current    30Days        60Days        90Days        120Days        Over120
      50                    1000.00       0.00        1500.00         100.00           0.00           0.00
      75                    2000.00     300.00         100.00        2300.00        3000.00        1000.00

Assumptions/Remarks:
    if trandate not found in AgingBase, Fields in AgingBaseWKS should be equal to 0.00
    re: AGINGBase     MemAcctID     Trandate                AgingWKS
                       50                07/31/2009            30Days     = 0.00
                  50                04/30/2009            120Days     = 0.00
                  50                03/31/2009            Over120     = 0.00

//Dependecies:
    dateex.cc
   UtilCompareAging.dbf

*/
//SET Additional Tools:
    set proc to dateex.cc additive // this proc is used to easily manipulate
                                            //    dates based on DUFLP
   dateex = new dateex()              // init var
   ? dateex.ldom(date())              // get last date of the month - testing only


//SET Variables:
    dYear        = 2009// Year(date()) or date set by user                                    //ex. 2009
    dCurrent = "08/31/2009" //current date or date set by user                       //ex. 08/31/2009  

   dMonth   = month(ctod(dCurrent))
   do case
       case (dMonth - 1) <= 0           
           d30        = dateex.ldom (ctod((dMonth - 1) + 12 + "/01/" + dYear))  //ex. 07/31/2009      
      case (dMonth - 1) > 0
          d30        = dateex.ldom (ctod(dMonth - 1 + "/01/" + dYear))           //ex. 07/31/2009      
   endcase

   do case
      case (dMonth - 2) <= 0           
           d60        = dateex.ldom (ctod((dMonth - 2) + 12 + "/01/" + dYear))  //ex. 06/30/2009      
      case (dMonth - 2) > 0
          d60        = dateex.ldom (ctod(dMonth - 2 + "/01/" + dYear))           //ex. 06/30/2009      
   endcase

   do case
      case (dMonth - 3) <= 0           
           d90        = dateex.ldom (ctod((dMonth - 3) + 12 + "/01/" + dYear))  //ex. 05/31/2009      
      case (dMonth - 3) > 0
          d90        = dateex.ldom (ctod(dMonth - 3 + "/01/" + dYear))           //ex. 05/31/2009      
   endcase

   do case
      case (dMonth - 4) <= 0           
           d120        = dateex.ldom (ctod((dMonth - 4) + 12 + "/01/" + dYear))  //ex. 04/30/2009      
      case (dMonth - 4) > 0
          d120        = dateex.ldom (ctod(dMonth - 4 + "/01/" + dYear))           //ex. 04/30/2009
   endcase

   do case
      case (dMonth - 5) <= 0           
           dOver120    = dateex.ldom (ctod((dMonth - 5) + 12 + "/01/" + dYear))  //ex. 03/31/2009      
      case (dMonth - 5) > 0
          dOver120    = dateex.ldom (ctod(dMonth - 5 + "/01/" + dYear))         //ex. 03/31/2009
   endcase  
//                                                                     /01/ because every first day of the month starts with 1 - LOL!  


dTHIGCI = new database()
dTHIGCI.databaseName := DATABASE_ALIAS   // from Settings.h
dTHIGCI.active := true


//set AgingBase
    qAgingBase = new query()
    with (qAgingBase)
      database := dTHIGCI
        sql := [SELECT * FROM AgingBase]
      active := true
    endwith

    rAgingBase = qAgingBase.rowset
   fAgingBase = rAgingBase.fields

   with (rAgingBase)
       indexName = "MemAcctID"
   endwith

//set AgingBaseWKS
   qAgingBaseWKS = new query()
    with (qAgingBaseWKS)
       database := dTHIGCI
      sql := [SELECT * ;
                FROM AgingBaseWKS ]
        active := true
   endwith

   rAgingBaseWKS = qAgingBaseWKS.rowset         
   fAgingBaseWKS = rAgingBaseWKS.fields

   with (rAgingBaseWKS)
       masterRowset = rAgingBase
      indexName = "MemAcctID"
   endwith


//reset utilcompareaging table
    dTHIGCI.emptyTable("UtilCompareAging")
   dTHIGCI.packTable("UtilCompareAging")

//set UtilCompareAging
   qUCA = new query()
    with (qUCA)
       database := dTHIGCI
      sql := [SELECT * ;
                FROM UtilCompareAging ]
        active := true
   endwith


   rUCA = qUCA.rowset         
   fUCA = rUCA.fields

   rAgingBase.first()
    rAgingBaseWKS.first()  

    for i = 1 to rAgingBase.count()  

      if rAgingBaseWKS.findkey(fAgingBase["MemAcctID"].value)

             
            //check here by date
            do case
               //current
               case fAgingBase["Trandate"].value = dCurrent
                  if fAgingBase["Amount"].value <> fAgingBaseWKS["current"].value
                     ?  "Current: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["current"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only                    
                     rUCA.beginAppend()
                         fUCA["ABMemAcctID"].value = fAgingBase["MemAcctID"].value
                        fUCA["ABTranDate"].value = fAgingBase["Trandate"].value
                        fUCA["ABAmount"].value = fAgingBase["Amount"].value
                        fUCA["ABWMemAcctID"].value = fAgingBaseWKS["MemAcctID"].value
                        fUCA["ABWAmount"].value = fAgingBaseWKS["Current"].value
                        fUCA["Aging"].value = "Current"
                       
                     rUCA.save()
                  endif
               //30 days
               case fAgingBase["Trandate"].value = d30
                  if fAgingBase["Amount"].value <> fAgingBaseWKS["30Days"].value
                     ?  "30Days:  " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["30days"].value + chr(9) + chr(9) + fAgingBase["amount"].value//test only
                     rUCA.beginAppend()
                         fUCA["ABMemAcctID"].value = fAgingBase["MemAcctID"].value
                        fUCA["ABTranDate"].value = fAgingBase["Trandate"].value
                        fUCA["ABAmount"].value = fAgingBase["Amount"].value
                        fUCA["ABWMemAcctID"].value = fAgingBaseWKS["MemAcctID"].value
                        fUCA["ABWAmount"].value = fAgingBaseWKS["30Days"].value
                        fUCA["Aging"].value = "30Days"                       
                     rUCA.save()
                  endif
               //60 days
               case fAgingBase["Trandate"].value = d60
                  if fAgingBase["Amount"].value <> fAgingBaseWKS["60Days"].value
                     ?  "60Days:  " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["60days"].value + chr(9) + chr(9) + fAgingBase["amount"].value//test only
                     rUCA.beginAppend()
                         fUCA["ABMemAcctID"].value = fAgingBase["MemAcctID"].value
                        fUCA["ABTranDate"].value = fAgingBase["Trandate"].value
                        fUCA["ABAmount"].value = fAgingBase["Amount"].value
                        fUCA["ABWMemAcctID"].value = fAgingBaseWKS["MemAcctID"].value
                        fUCA["ABWAmount"].value = fAgingBaseWKS["60Days"].value
                        fUCA["Aging"].value = "60Days"
                       
                     rUCA.save()
                  endif
               //90 days
               case fAgingBase["Trandate"].value = d90
                  if fAgingBase["Amount"].value <> fAgingBaseWKS["90Days"].value
                     ?  "90Days:  " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["90days"].value + chr(9) + chr(9) + fAgingBase["amount"].value//test only
                            rUCA.beginAppend()
                         fUCA["ABMemAcctID"].value = fAgingBase["MemAcctID"].value
                        fUCA["ABTranDate"].value = fAgingBase["Trandate"].value
                        fUCA["ABAmount"].value = fAgingBase["Amount"].value
                        fUCA["ABWMemAcctID"].value = fAgingBaseWKS["MemAcctID"].value
                        fUCA["ABWAmount"].value = fAgingBaseWKS["90Days"].value
                        fUCA["Aging"].value = "90Days"
                       
                     rUCA.save()
                  endif
               //120 days
               case fAgingBase["Trandate"].value = d120
                  if fAgingBase["Amount"].value <> fAgingBaseWKS["120Days"].value
                     ?  "120Days: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["120days"].value + chr(9) + chr(9) + fAgingBase["amount"].value//test only
                     rUCA.beginAppend()
                         fUCA["ABMemAcctID"].value = fAgingBase["MemAcctID"].value
                        fUCA["ABTranDate"].value = fAgingBase["Trandate"].value
                        fUCA["ABAmount"].value = fAgingBase["Amount"].value
                        fUCA["ABWMemAcctID"].value = fAgingBaseWKS["MemAcctID"].value
                        fUCA["ABWAmount"].value = fAgingBaseWKS["120Days"].value
                        fUCA["Aging"].value = "120Days"
                       
                     rUCA.save()
                  endif
               //over120 days
               case fAgingBase["Trandate"].value = dOver120
                  if fAgingBase["Amount"].value <> fAgingBaseWKS["Over120"].value
                     ?  "Over120: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["over120"].value + chr(9) + chr(9) + fAgingBase["amount"].value//test only
                     rUCA.beginAppend()
                         fUCA["ABMemAcctID"].value = fAgingBase["MemAcctID"].value
                        fUCA["ABTranDate"].value = fAgingBase["Trandate"].value
                        fUCA["ABAmount"].value = fAgingBase["Amount"].value
                        fUCA["ABWMemAcctID"].value = fAgingBaseWKS["MemAcctID"].value
                        fUCA["ABWAmount"].value = fAgingBaseWKS["Over120"].value
                        fUCA["Aging"].value = "Over120"
                       
                     rUCA.save()
                  endif
            endcase

            //check here content of AgingBaseWKS if it has 0.00 value
            //upon which no record should have been appended to
            //Aging base in relation to aging which has 0.00 value
            do case
                case fAgingBaseWKS["Current"].value = 0.00 AND fAgingBase["Trandate"].value = dcurrent
                   ?  "Current: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["current"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only
                    case fAgingBaseWKS["30Days"].value = 0.00 AND fAgingBase["Trandate"].value = d30
                   ?  "30Days: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["30Days"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only
               case fAgingBaseWKS["60Days"].value = 0.00 AND fAgingBase["Trandate"].value = d60
                   ?  "60Days: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["60Days"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only
               case fAgingBaseWKS["90Days"].value = 0.00 AND fAgingBase["Trandate"].value = d90
                   ?  "90Days: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["90Days"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only
                    case fAgingBaseWKS["120Days"].value = 0.00 AND fAgingBase["Trandate"].value = d120
                   ?  "120Days: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["120Days"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only
               case fAgingBaseWKS["Over120"].value = 0.00 AND fAgingBase["Trandate"].value = dOver120
                   ?  "Over120: " + fAgingBase["MemAcctID"].value + chr(9) + fAgingBase["Trandate"].value + chr(9) + fAgingBaseWKS["Over120"].value + chr(9) + chr(9) + fAgingBase["amount"].value //test only
                  
            endcase
        else
          ? fAgingBaseWKS["MemAcctID"].value // check what memacctID has been saved in AgingBaseWKS
                                                       //that is not present in AgingBASE
      endif

      rAgingBase.next()
   endfor

? "AgingBase RecordCount: " + chr(9) + chr(9) +rAgingBase.count()
? "AgingBaseWKS RecordCount:" + chr(9)  +rAgingBaseWKS.count()

qAgingBase.active = false
qAgingBaseWKS.active = false
qUCA.active = false
dTHIGCI.active = false

Thursday, October 8, 2009

When nudity is art.. LOL

Wednesday, October 7, 2009

A visit to Greenlands

It was another work visit at Tagaytay Highlands but all seem to be a vacation because entering the pave way of said facet will surely relax anybody's aching nerve as you will be welcomed with fresh and really cool ambiance.

Down to midlands, my workmate, Nikki, needs to enhance his developed Point-Of-Sale (POS) Software. Apparently, the Taal view gets nearer while landscapes are so awesome, portraits of which are worth more than a memento.

After having lunch at Midlands, we traversed around Greenlands, adjacent land development of Highlands. Passing by the winding roads, I was really captivated by the different magnificent architectural designs made for sure by brilliant architects since owners are from the elite society. Such homes include Mediterranean, European, American and Japanese-Inspired aesthetics to name a few. Near Lake view, owner of SM's home can be located. If you happen to see posters of SM residences, it has something to do with the latter.

Anyone among you who has happen to pass around Tarragon court, corner Chili already? We'll guess who's the owner of the home located in such.



It's Wowowee's host.
As of this post date, the home in front of it is for sale. Try deal.. email me and I'l tell you how much.. Architect of said home is Bryan Tan, according to the poster posted in front..

Thursday, October 1, 2009

Pincrest Village at Tagaytay Highlands

Gusto ko lamang pong i-share ang larawan ng Pinecrest Village kung saan dito ako kalimitang pinatitira ng boss q tuwing may overnight stay kami sa Tagaytay Highlands.

Pwede niyo pong tingnan ang kabuuan at kung paano makakapunta sa tagaytay highlands sa pamamagitan ng kanilang website:
http://www.tagaytayhighlands.com/

Salamat po.


Pinecrest Village





Pinecrest Village was Tagaytay Highlands' first residential project, meticulously designed to cater to the discriminating tastes of Highlands members. Renowned architects Pablo Antonio and Nonoy Hubilla artfully crafted wood and stone to evoke the look and feel of a remote, yet intimate Swiss-Alpine village. Pinecrest Village is exclusive to members of the Highlands and Midlands Golf and Country Clubs.




167 condominium units in one-, two-, and three-bedroom models

with floor areas ranging from 85 to 180 sq.m.

covering approximately four hectares and situated right next to the Highlands golf course hole number 2

spectacular views of Taal Lake, Laguna de Bay, Mount Makiling, Mount Banahaw and the Batangas countryside from every unit

All units outfitted with European-style fixtures

A gated community with 24-hour security

with individual parking lots

ample water supply through the privately-owned Tagaytay Highlands water system

with fire sprinklers system

whirlpool tub in every master's bedroom

24/7 emergency care unit

povided with 100% emergency power supply

telephone and cable television provisions

Launched in 1994


Sunday, September 27, 2009

Principles of Programming Languages - Module 5

Module 5      
Elementary Data Type

A data type is a class of data objects together with a set of operations for creating and manipulating them.

An elementary data object contains a single data value.  A class of such data objects over which various operations are defined is termed an elementary data type.

The basic elements of a specification of an elementary data type are as follows:
1. Attributes that distinguish data objects of that type. 
2. Values  that data objects of that type may have.  The type of a data object determines the set of possible(maximum) values that it may contain.  The set of values defined by an elementary data type is usually an ordered set with a least value and a greatest value; for any pair of distinct values, one is greater than the other.
3. Operations that define the possible manipulations of data objects of that type.  They may be  primitive which means that they are specified as part of the language definition, or they may be programmer-defined operations, in the form of subprograms or method declarations as part of class definitions.  Examples: integer addition, the use of the equal symbol to test equality, square-root operation

Implementation of Elementary Data Types

The implementation of an elementary data type consists of a storage representation for data objects and values of that type, and a set of  algorithms  or  procedures that define the operations of the type in terms of manipulations of the storage representation.

Storage Representation

Storage for elementary data types is strongly influenced by the under lying computer that will execute the program.  For example, the storage representation for integer or real values is almost always the integer or floating-point binary representation for numbers used in the underlying hardware.

The representation of a data object is ordinarily independent of its location in memory.  The storage representation is usually described in terms of the size of the block of the memory required(the number of memory words, bytes, or bits needed) and the layout of the attributes and data values within its block.  Usually the address of the first word or byte of such a block of memory is taken to represent the location of the data object.

Implementation of operations

Each operation defined for data objects of a given type may be implemented in one of three main ways:
1. Directly as hardware operation.  For example, if integers are stored using hardware representation for integers, then addition and subtraction are implemented using the arithmetic operations built into the hardware.
2.  As a procedure or function subprogram.  For example, a square-root operation is usually not provided directly as hardware operation.  It might be implemented as a square-root subprogram that calculates the square root of its argument.
3. As an inline code sequence.  An inline code sequence is also a software implementation of the operation.  However, instead of using a subprogram, the operations in the subprogram are copied into the program at the point where the subprogram would otherwise have been invoked.  For example, the absolute-value function  on numbers,  defined by  abs(x) = if x < 0 then -x else x is usually implemented as an inline code sequence:
a.  Fetch value of x from memory.
b.  If x > 0, skip the next instruction.
c.  Set x = -x.
d. Store new value of x in memory.
Each line is implemented by a single-hardware operation.

Declaration

A declaration  is a program statement that serves to communicate to the language translator information about the name and type of data objects needed during program execution.  By its placement in the program (e.g. within a particular subprogram or class definition), a declaration may also serve to indicate the desired lifetimes of the data objects.

Sample declarations of some programming languages:

• The C declaration float A, B; at the start of a subprogram indicates that two data objects of type float are needed during execution of the subprogram.  This is an example of an explicit declaration.
• FORTRAN is a programming language that provides implicit or default declarations, which are declarations that hold when no explicit declaration is given.  The variable INDEX may be used without explicit declaration; it is assumed by the compiler to be an integer variable because its name begins with one of  the letters I-N. 
• In Perl, simply assigning a value to a variable declares  the type of the variable
Examples:  $MyVar = 'This is a string'    # $MyVar is now a string variable
      $MyVar = 890                   # $MyVar is now an integer variable

The most important purpose for declarations, from the programmer's viewpoint, is that they allow for static rather than dynamic type checking.

Data storage representations that are built into the computer hardware usually include no type information, and the primitive operations on the data do no type checking.  For example, a particular word in the computer memory during execution of a program may contain the bit sequence 101010010100…1001 may represent an integer, a real  number, a sequence of characters, or an instruction.  The hardware primitive operation for integer addition cannot check whether its two arguments represents integers; they are simply bit sequences.  At the hardware level, conventional computers are particularly unreliable in detecting data type errors.

Type checking means the checking that each operation executed by a program receives the proper number of arguments of the proper data types.  For example given the expression X = A + B * C, the compiler must determine for each operation(addition, multiplication, and assignment) that each receives two arguments of the proper data type.

Type checking may be done at run time (dynamic type checking) or at compile time (static type checking).

Dynamic type checking  is run-time type checking usually performed immediately before the execution of a particular operation.  It is usually implemented by storing  a type tag in each data object that indicates the data type of the object.  For example, an integer data object would contain both the integer value and an integer type tag.

Scalar Data Types

Scalar data objects have a single attribute for its data object.  For example, an integer object has an integral value (ex. 130, -90, 12), and no other information can be obtained from that object.  They also follow the hardware architecture of a computer (e.g. integers, floating-points, characters).

Integers

The set of integer values defined for the type forms an ordered subset, within some finite bounds, of the infinite set of integers studied in mathematics.  The maximum integer value is sometimes represented as a defined costant.

Operations on these data objects include:
• Arithmetic
• Relational
• Assignment
• Bit

Floating-Point Real Numbers

A floating-point real number data type is often specified with only the single data type  attribute real, as in ForTran, or float, as in C.  The values form an ordered sequence from some hardware-determined minimum negative value to a maximum value, but the values are not distributed evenly across this range.  The precision required for floating-point numbers, in terms of the number of digits used in the decimal representation, may be specified by the programmer.

Operations on these data objects include:
• Arithmetic
• Relational
• Assignment
• Bit

Boolean operations on these objects are sometimes restricted.  Due to roundoff issues, equality between two real numbers is rarely achieved.

Fixed-Point Real Numbers

Data objects like money which contains pesos and cents, and other values which are rational that requires two or specific number of decimal places, should not be written as integers or floating-point values to avoid roundoff errors.  Thus, a form of fixed-point data should be used to represent these values.

A fixed number is represented as a digit sequence of fixed length, with the decimal point positioned at a given point between two digits.

Complex numbers

This numeric data type consists of a pair of numbers representing the number's real and imaginary parts.

Rational Numbers

A rational number is the quotient of two integers.  It is included in a programming language to avoid the problems of roundoff and truncation encountered in floating and fixed point representations of reals.

Enumerations

An ordered list of distinct values is called an enumeration.  Languages such as C, and C++ include an enumeration data type that allows the programmer to define and manipulate such variables more directly.

Below is sample program that uses the enum data type:

#include
#include
#include

void main()
{
enum x {One, Two, Three};
x y = Three;
clrscr();
if (y == 2)
cout << "Three"<< endl;
getch();
}

Booleans

Most languages provide a data type for representing true or false, usually called a Boolean or logical data type.

The most common operations on Boolean types include assignment as well as the following logical operations:
• And - Conjunction
• Or - Inclusive disjunction
• Not - Negation or complement

Characters

A character data type provides data objects that have a single character as their value.   The set of possible character values is usually taken to be a language-defined enumeration corresponding to the standard character sets supported by the underlying hardware and operating system, such as the ASCII character set. 

The ordering of the characters in this character set is called the collating sequence for the character set. Collating sequence is important because it determines the alphabetical ordering given to character strings by the relational operations.  Spaces, digits, and special characters may be alphabetized as well.

Operations include:

• Relational
• Assignment
• Testing whether a character value is one of the special classes letter, digit, or special character

Composite Data Types
Elementary data types may involve a complex data structure organization by the compiler.  Thus, multiple attributes  are often given for each such data type.

Character Strings

These are objects that composed of a sequence of characters.

There are at least three different treatments of character-string data types :

• Fixed declared length.  A character-string data object may have a fixed length that is declared in the program.
• Variable length to a declared bound.  A character-string data object may have a maximum length that is declared in the prior program, but the actual value stored in the data object may be a string  of shorter length-possibly even the empty string of no characters.
• Unbounded length.  A character-string data object may have a string value of any length, and the length may vary dynamically during execution  with no bound (beyond available memory).

Operations on Strings:
• Concatenation - an operation of joining two character strings to make one long string
• Relational operations on strings - use of logical operators like the less than, greater than symbols, etc.
• Substring selection using positioning subscripts - extracting substrings through positioning subscripts
• Input-output formatting - formatting of strings when read or displayed
• Substring selection using pattern matching - - extracting substrings through pattern matching
• Dynamic strings - The language Perl supports static and dynamic strings.  The string '$ABC' is static, and the statement print '$ABC'; will print the value $ABC.  The string "$ABC" is dynamic and the statement print "$ABC"; will cause the string to be evaluated, and the value of the Perl variable $ABC is printed instead.

Pointers

A pointer is also called a reference or access type.  It contains the location of another data object or may contain the null pointer, nil or null.  Pointers are ordinary data objects that may be simple variables or components of arrays and records.

Files and Input-Output

A file  is a data structure with two special properties:
1. It ordinarily is represented on a secondary storage device such as a disk or tape and thus may be much larger than the most data structures of other types.
2. Its lifetime may encompass a greater span of time than that of the program creating it.

Sequential Files

These are the most common type of file.  It is a data structure composed of a linear sequence of components of the same type.
Operations

• Open - this operation ordinarily requests information from the operating system about the location and properties of the file, allocates the required internal storage for buffers and other information, and sets the file-position pointer to the first component of the file.
• Read - this operation transfers the contents of the current file component to a designated variable in the program
• Write - this operation creates a new component at the current position in the file(always at the end) and transfers the contents of a designated program variable to the new component.
• End-of-file test - A read operation fails if the file position pointer designates the end of the file.  Because the file is of variable length, an explicit test for the end-of-file position is needed so that the program may take special action.
• Close - this operation involves notification to the operating system that the file can be detached from the program (and potentially made available to other programs) and possibly also deallocation of internal storage used for the file (such as buffers and buffer variables) (Pratt, and Zelkowitz, 2001)

Principles of Programming Languages - Module 4

Module 4  
Names, Bindings, Type Checking and Scopes

Names

One of the fundamental attributes of variables is names, which have broader use than simply for variables.  They are also associated with labels, subprograms, formal parameters, and other program constructs.  The term identifier is often used interchangeably with name.

Name forms

A name is a string of characters used to identify some entity in a program.  The earliest programming languages used single-character names.  This was natural because early programming was primarily mathematical, and mathematicians have long used single-character names for unknowns in their formal notations.

A programming language has a maximum length of a name. For example, FORTRAN 90 and C allow up to 31 characters. Ada names have no length limit.  Some languages like C++, do not specify a length limit on names.

The commonly acceptable name form is a string with a reasonably long length limit, if any, with some connector character such as the underscore(_) included.  The underscore serves the same purpose as a space in English text but without terminating the name string in which it is placed.

In some languages, like C, C++, and Java, uppercase and lowercase letters in names are distinct; that is, names in these languages are case sensitive.

Special Words

Special words in programming languages are used to make programs more readable by naming actions to be performed.  They are  used to separate the syntactic entities of programs.  In most languages, these words are classified as reserved words, but in some they are only keywords.

A keyword is a word of a programming language that is special only in certain contexts.  A reserved word is a special word  of a programming language that cannot be used as a name.  As a language design choice, reserved words are better than keywords because the ability to redefine keywords can lead to readability problems.

Variables

A program variable is an abstraction of a computer memory cell or collection of cells.  Programmers often think of variables as names for memory locations, but there is much more to a variable than just a name.  A variable can be characterized as a sextuple of attributes: (name, address, value, type, lifetime, scope).
Address

The address of a variable is the memory address with which it is associated.  It is sometimes called its l-value, because that is what is required when a variable appears in the left side of an assignment statement.

Aliases

It is possible to have multiple identifiers reference the same address.  When more than one variable name can be used to access a single memory location, the names are called aliases.  Aliasing is a hindrance to readability because it allows  a variable to have its value changed by an assignment to a different variable.

Type

The type of a variable determines the range of values the variable can have and the set of operations that are defined for values of the type.

Value

The value of a variable is the contents of the memory cell or cells associated with the variable.  It is convenient to think of computer memory in terms of abstract cells, rather than physical cells.  It is sometimes called the variable's r-value because it is what is required when the variable is used on the right side of an assignment statement.


Bindings

Binding is an association such as between an attribute and an entity or between an operation and a symbol.  The time at which a binding takes place is called binding time. Bindings can take place at language design time, language implementation time, compile time, link time, load time, or load time. 

Examples:
• The asterisk symbol(*) is usually bound to the multiplication operation at language design time.
• A variable in C or C++ program is bound to as particular data type at compile time.
• A variable may be bound to a storage cell when the program is loaded to the memory
• A call to a library subprogram is bound to the subprogram code at link time.

Given some lines of a C++ program:

int iCt;
…
iCt = iCt + 1;

Some of the bindings and their binding times for the parts of this assignment statement are as follows:
• Set of possible types for iCt:  bound at language design time.
• Type of count:  bound at compile time.
• Set of possible values of iCt: bound at compiler design time.
• Value of iCt: bound at execution time with this statement.
• Set of possible meanings for the operator symbol +:  bound at language definition time.
• Meaning of the operator symbol + in this statement:  bound at compile time.
• Internal representation of the literal 1:  bound at compiler design time.

A binding is static if it occurs before run time and remains unchanged throughout program execution.  If it occurs during run time or can change in the program execution, it is called dynamic.

Type Bindings

Before a variable can be referenced in a program, it must be bound to a data type.  The two important aspects of this binding are (1) how the type is specified and (2) when the binding takes place.

Forms of Variable Declaration
1. Explicit declaration - a statement in a program that lists variable names and specifies that they are a particular type.
2. Implicit declaration - a means of associating variables with types  through default conventions instead of declaration statements.

The first appearance of a variable name in a program constitutes its implicit declaration.  Both explicit and implicit declarations create static binding to types.

Dynamic Type Binding

With dynamic type binding, the type is not specified by a declaration statement.  Instead, the variable is bound to a type when it is assigned a value in an assignment statement. When the assignment statement is executed, the variable being assigned is bound to the type of the value, variable, or expression on the right side of the assignment.

One of its advantages is that it provides a great deal of programming flexibility.  With dynamic type binding, one can deal with data of any type.

Dynamic type binding has also disadvantages. One of these is the error detection capability of the compiler is diminished relative to a compiler for a language with  static type bindings, because any two types can appear on opposite sides of the assignment operator.  Incorrect types of right sides of assignments are not detected as errors; rather, the type of the left side is simply changed to the incorrect type.

Type Inference

For programming languages like ML, Miranda, and Haskell, with type inference, the types of most expressions can be determined without requiring the programmer to specify the types of the variables

Type Checking

When dealing with type checking, one has to consider the following:
1. Subprograms will be taken as operators whose operands are their parameters;
2. The assignment symbol will be thought of  as a binary operator, with its target variable and its expression being the operands.

Type checking is the activity of ensuring that the operands of an operator are of compatible types.  A compatible type is one that is either legal for the operator or is allowed under language rules to be implicitly converted by compiler-generated code to a legal type which is known as coercion.  A type error is the application of an operator to an operand of an inappropriate type.

Strong Typing

This is one of the new ideas in language design that became prominent in the so-called structured programming revolution of the 1970s. A strongly typed language is one in which each name in a program in the language has a single type associated with it, and that type is known at compile time.  A programming language is considered strongly typed if type errors are always detected.  The importance of strong typing lies in its ability to detect all misuses of variables that result in type errors.  Languages like FORTRAN, C and C++ are not strongly typed.  Examples of programming languages that are nearly strongly typed are Pascal and Ada.  Languages like ML and Java are strongly typed.

Type Compatibility

The design of the type compatibility rules of a language is important, because it influences the design of the data types and operations provided for values  of those types.

Two different type compatibility methods:
1. Name compatibility -  this means that two variables have compatible types only if they are  in either the same declaration or in declarations that use the same type name.
2. Structure compatibility - this means that two variables have compatible types if their types have identical structures.

Scope

One of the most important factors having an effect on the understanding of variables is scope.  The scope of a program variable is defined as the range of statements in which the variable is visible.  A variable is visible in a statement if it can be referenced in that statement  A variable is local in a program unit or block if it is declared there.  The nonlocal variables of a program unit or block are those that are visible within the program unit or block but are not declared there. (Sebesta)

Principles of Programming Languages - Module 3

Module 3 
Describing Syntax  and Semantics

The study of programming languages, like the study of natural languages, can be divided into examinations of syntax and semantics.  The syntax of a programming language is the form of its expressions, statements, and program units.  Its semantics is the meaning of those expressions, statements, and program units.  For example, the syntax of a C if  statement is if () .  The semantics of this statement form is that if the current value of the expression is true, the embedded statement is selected for execution.

Syntax and semantics are closely related.  In a well-designed programming language, semantics, should follow directly from syntax; that is, the form of statement should strongly suggest what the statement is meant to accomplish.

Languages, whether natural (such as English) or artificial (such as Java), are sets of strings of characters from some alphabet.  The strings of a language are called sentences or statements.  The syntax rules of a language specify which strings of characters from the language's alphabet are in the language. 

Formal descriptions of the syntax of programming languages, often do not include descriptions of the lowest level syntactic units.  These small units are called lexemes.  The lexemes of a programming language include its identifiers, literals, operators, and special words.

A  token  of a language is a category of its lexemes.  An identifier is a token that can have lexemes, or instances.  In some cases, a token has only a single possible lexeme. 

For example:

Given  the C statement:  index = 2 * count + 20;

The lexemes and tokens of this statement

Lexemes        Tokens
index              identifier
=                     equal_sign
2                     int_literal
*                      mult_op
count              identifier
+                     plus_op
20                   int_literal
;                      semicolon

A Grammar for Simple Assignment Statements

Given:   a = b * ( a + c )

    =
      a =
                    a = *
                    a = b *
                    a = b * ( )
                    a = b * ( + )
                    a = b  * ( a + )
                    a = b * ( a +
                    a = b *  ( a + c)

Parse Trees

One of the most attractive features of grammars is that they naturally describe the hierarchical syntactic structure of the sentences of the languages they define.  These structures are called parse trees.

Given: a = b * ( a + c )

Ambiguity

A grammar that generates a sentence for which there are two or more distinct parse trees is said to be ambiguous.

Given: a = b *  a + c
Note:  The parse tree will be supplied by the teacher in class.

Operator Precedence

A parse tree of a sentence with multiple operators, regardless of the particular operators involved, has the rightmost operator in the expression at the lowest point in the parse tree, with the other operators in the tree moving progressively higher as one moves to the left in the expression. 

Static Semantics

The static semantics of a language is only indirectly related to the meaning of programs during execution; rather, it has to do with the legal forms of programs (syntax rather than semantics).  In many cases, the static semantic rules of a language state its type constraints.  Static semantics is so named because the analysis required to check these specifications can be done at compile time.

Denotational Semantics

This is the most rigorous widely know method for describing the meaning of programs.  The fundamental concept of denotational semantics is to define for each language entity both a mathematical object and a function that maps instances of that entity onto instances of the   mathematical object.
Related Posts with Thumbnails