home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 3 / AACD03.BIN / AACD / Programming / sofa / archive / SmallEiffel.lha / SmallEiffel / lib_std / general.e < prev    next >
Text File  |  1999-06-05  |  20KB  |  674 lines

  1. -- This file is  free  software, which  comes  along  with  SmallEiffel. This
  2. -- software  is  distributed  in the hope that it will be useful, but WITHOUT 
  3. -- ANY  WARRANTY;  without  even  the  implied warranty of MERCHANTABILITY or
  4. -- FITNESS  FOR A PARTICULAR PURPOSE. You can modify it as you want, provided
  5. -- this header is kept unaltered, and a notification of the changes is added.
  6. -- You  are  allowed  to  redistribute  it and sell it, alone or as a part of 
  7. -- another product.
  8. --          Copyright (C) 1994-98 LORIA - UHP - CRIN - INRIA - FRANCE
  9. --            Dominique COLNET and Suzanne COLLIN - colnet@loria.fr 
  10. --                       http://SmallEiffel.loria.fr
  11. --
  12. class GENERAL
  13.    --
  14.    -- Platform-independent universal properties.
  15.    -- This class is an ancestor to all developer-written classes.
  16.    --
  17.  
  18. feature -- Access :
  19.    
  20.    generating_type: STRING is
  21.          -- Name of current object's generating type (type of 
  22.          -- which it is a direct instance).
  23.       external "SmallEiffel"
  24.       end;
  25.   
  26.    generator: STRING is
  27.          -- Name of current object's generating class (base class
  28.          -- of the type of which it is a direct instance).
  29.       external "SmallEiffel"
  30.       end;
  31.    
  32.    stripped(other: GENERAL): like other is
  33.       -- Newly created object with fields copied from current object,
  34.       -- but limited to attributes of type of `other'.
  35.       require
  36.          conformance: conforms_to(other);
  37.       do
  38.          not_yet_implemented;
  39.       ensure
  40.          stripped_to_other: Result.same_type(other);
  41.       end;
  42.    
  43. feature -- Status report :
  44.    
  45.    frozen conforms_to(other: GENERAL): BOOLEAN is
  46.          -- Is dynamic type of `Current' a descendant of dynamic type of
  47.          -- `other' ?
  48.          -- 
  49.          -- Note: because of automatic conversion from expanded to reference
  50.          -- type when passing argument `other', do not expect a correct  
  51.          -- behavior with  expanded types.
  52.       require 
  53.          not is_expanded_type;
  54.          other_not_void: other /= Void
  55.       do
  56.          Result := other.se_assigned_from(Current);
  57.       end;
  58.  
  59.    frozen same_type(other: GENERAL): BOOLEAN is
  60.          -- Is type of current object identical to type of `other' ?
  61.       require
  62.          not is_expanded_type;
  63.          other_not_void: other /= Void
  64.       do
  65.          if conforms_to(other) then
  66.             Result := other.conforms_to(Current);
  67.          end;
  68.       ensure
  69.          definition: Result = (conforms_to(other) 
  70.                                and 
  71.                                other.conforms_to(Current));
  72.       end;
  73.    
  74. feature -- Comparison :
  75.    
  76.    frozen equal(some: ANY; other: like some): BOOLEAN is
  77.          -- Are `some' and `other' both Void or attached to
  78.          -- objects considered equal ?
  79.       do
  80.          if some = other then
  81.             Result := true;
  82.          elseif some = Void then
  83.          elseif other = Void then
  84.          else
  85.             Result := some.is_equal(other);
  86.          end;
  87.       ensure
  88.          definition: Result = (some = Void and other = Void) or else
  89.                      ((some /= Void and other /= Void) and then
  90.                       some.is_equal(other));
  91.       end;
  92.  
  93.    is_equal(other: like Current): BOOLEAN is
  94.          -- Is `other' attached to an object considered equal to 
  95.          -- current object ?
  96.       require
  97.          other_not_void: other /= Void
  98.       external "SmallEiffel"
  99.       ensure
  100.          consistent: standard_is_equal(other) implies Result;
  101.          symmetric: Result implies other.is_equal(Current);
  102.       end;
  103.    
  104.    frozen standard_equal(some: ANY; other: like some): BOOLEAN is
  105.          -- Are `some' and `other' both Void or attached to
  106.          -- field-by-field objects of the same type ?
  107.          -- Always use the default object comparison criterion.
  108.       do
  109.          if some = other then
  110.             Result := true;
  111.          elseif some = Void then
  112.          elseif other = Void then
  113.          elseif some.same_type(other) then
  114.             Result := some.standard_is_equal(other);
  115.          end;
  116.       ensure
  117.          definition: Result = (some = Void and other = Void) or else
  118.                      ((some /= Void and other /= Void) and then
  119.                       some.standard_is_equal(other));
  120.       end;
  121.  
  122.    frozen standard_is_equal(other: like Current): BOOLEAN is
  123.          -- Are Current and `other' field-by-field identical?
  124.       require
  125.          other /= Void
  126.       external "SmallEiffel"
  127.       ensure
  128.          symmetric: Result implies other.standard_is_equal(Current);
  129.       end;
  130.    
  131. feature -- Deep Comparison :
  132.  
  133.    deep_equal, frozen standard_deep_equal(some: ANY; other: like some):
  134.                                                                  BOOLEAN is
  135.          -- Are `some' and `other' either both Void or attached to 
  136.          -- recursively isomorphic object structures ?
  137.       do
  138.          if some = other then
  139.             Result := true;
  140.          elseif some = Void then
  141.          elseif other = Void then
  142.          elseif standard_equal(some,other) then
  143.             Result := true;
  144.          else
  145.             Result := some.is_deep_equal(other);
  146.          end;
  147.       ensure
  148.          shallow_implies_deep: standard_equal(some,other) implies Result;
  149.          same_type: Result implies some.same_type(other);
  150.          symmetric: Result implies deep_equal(other,some);
  151.       end;
  152.    
  153.    is_deep_equal(other: like Current): BOOLEAN is
  154.          -- Is `Current' recursively isomorph with `other' ?
  155.       require
  156.          other_not_void: other /= Void
  157.       do
  158.          if Current = other then
  159.             Result := true;
  160.          elseif other = Void then
  161.          elseif standard_is_equal(other) then
  162.             Result := true;
  163.          else
  164.             not_yet_implemented;
  165.          end;
  166.       ensure
  167.          symmetric: Result implies other.is_deep_equal(Current);
  168.       end;
  169.    
  170. feature -- Duplication :
  171.    
  172.    frozen clone(other: ANY): like other is
  173.          -- When argument `other' is Void, return Void
  174.          -- otherwise return `other.twin'.
  175.       do
  176.          if other /= Void then
  177.             Result := other.twin;
  178.          end;
  179.       ensure
  180.          equal: equal(Result,other);
  181.       end;
  182.  
  183.    frozen twin: like Current is
  184.          -- Return a new object with the dynamic type of Current.
  185.          -- Before being returned, the new object is initialized using
  186.          -- feature `copy' (Current is passed as the argument).
  187.          -- Thus, when feature `copy' of GENERAL is not redefined, 
  188.          -- `twin' has exactly the same behaviour as `standard_twin'.
  189.       external "SmallEiffel"
  190.       ensure
  191.          equal: Result.is_equal(Current);
  192.       end;
  193.  
  194.    copy(other: like Current) is
  195.          -- Update current object using fields of object attached
  196.          -- to `other', so as to yield equal objects.
  197.       require
  198.          other_not_void: other /= Void
  199.       external "SmallEiffel"
  200.       ensure
  201.          is_equal: is_equal(other)
  202.       end;
  203.    
  204.    frozen standard_clone(other: ANY): like other is
  205.          -- Void if `other' is Void; otherwise new object 
  206.          -- field-by-field identical to `other'. 
  207.          -- Always use the default copying semantics.
  208.       do
  209.          if other /= Void then
  210.             Result := other.standard_twin;
  211.          end;
  212.       ensure
  213.          equal: standard_equal(Result,other);
  214.       end;
  215.  
  216.    frozen standard_twin: like Current is
  217.          -- Return a new object with the dynamic type of Current.
  218.          -- Before being returned, the new object is initialized using
  219.          -- feature `standard_copy' (Current is passed as the argument).
  220.       external "SmallEiffel"
  221.       end;
  222.       
  223.    frozen standard_copy(other: like Current) is
  224.          -- Copy every field of `other' onto corresponding field of 
  225.          -- current object.
  226.       require
  227.          other_not_void: other /= Void
  228.       external "SmallEiffel"
  229.       ensure
  230.          standard_is_equal(other);
  231.       end;
  232.    
  233. feature -- Deep Duplication :
  234.  
  235.    deep_clone(other: GENERAL): like other is
  236.          -- Void if `other' is Void: otherwise, new object structure 
  237.          -- recursively duplicated from the one attached to other.
  238.       do
  239.          not_yet_implemented;
  240.       ensure
  241.          deep_equal: deep_equal(other,Result);
  242.       end;
  243.    
  244. feature -- Basic operations :
  245.    
  246.    frozen default: like Current is
  247.          -- Default value of current type.
  248.       do
  249.       end;
  250.    
  251.    frozen default_pointer: POINTER is
  252.          -- Default value of type POINTER (avoid the need to
  253.          -- write p.default for some `p' of type POINTER).
  254.       do
  255.       ensure
  256.          Result = Result.default;
  257.       end;
  258.    
  259.    default_rescue is
  260.          -- Handle exception if no Rescue clause.
  261.          -- (Default: do nothing.)   
  262.       do
  263.       end;
  264.    
  265.    frozen do_nothing is
  266.          -- Execute a null action.
  267.       do
  268.       end;
  269.    
  270. feature -- Input and Output :
  271.    
  272.    io: STD_INPUT_OUTPUT is
  273.          -- Handle to standard file setup.
  274.          -- To use the standard input/output file.
  275.          -- Has type STD_FILES in ELKS 95.
  276.       once
  277.          !!Result.make;
  278.       ensure
  279.          Result /= Void;
  280.       end; 
  281.    
  282.    std_input: STD_INPUT is
  283.          -- To use the standard input file.
  284.       once
  285.          !!Result.make;
  286.       end; 
  287.    
  288.    std_output: STD_OUTPUT is
  289.          -- To use the standard output file.
  290.       once
  291.          !!Result.make;
  292.       end; 
  293.    
  294.    std_error: STD_ERROR is
  295.          -- To use the standard error file.
  296.       once
  297.          !!Result.make;
  298.       end; 
  299.    
  300. feature -- Object Printing :
  301.  
  302.    frozen print(some: GENERAL) is
  303.          -- Write terse external representation of `some' on
  304.          -- `standard_output'.
  305.          -- To customize printing, one may redefine 
  306.          -- `fill_tagged_out_memory' or `out_in_tagged_out_memory' (see 
  307.          -- for example how it works in class COLLECTION).
  308.       -- Not frozen in ELKS 95.
  309.       do
  310.          if some = Void then
  311.             std_output.put_string("Void");
  312.          else
  313.             some.print_on(std_output);
  314.          end;
  315.       end;
  316.    
  317.    print_on(file: OUTPUT_STREAM) is
  318.          -- Default printing of current object on a `file'.
  319.          -- One may redefine `fill_tagged_out_memory' or 
  320.          -- `out_in_tagged_out_memory' to adapt the behavior of 
  321.          -- `print_on'.
  322.          --
  323.       do
  324.          tagged_out_memory.clear;
  325.          out_in_tagged_out_memory;
  326.          file.put_string(tagged_out_memory);
  327.       end;
  328.  
  329.    frozen tagged_out: STRING is
  330.          -- New string containing printable representation of current 
  331.          -- object, each field preceded by its attribute name, a 
  332.          -- colon and a space.
  333.       do
  334.          tagged_out_memory.clear;
  335.          fill_tagged_out_memory;
  336.          Result := tagged_out_memory.twin;
  337.       end;
  338.    
  339.    out: STRING is
  340.          -- Create a new string containing terse printable 
  341.          -- representation of current object.
  342.       do
  343.          tagged_out_memory.clear;
  344.          out_in_tagged_out_memory;
  345.          Result := tagged_out_memory.twin;
  346.       end;
  347.    
  348.    out_in_tagged_out_memory is
  349.          -- Append terse printable represention of current object
  350.          -- in `tagged_out_memory'.
  351.       do
  352.          tagged_out_memory.append(generating_type);
  353.          if not is_expanded_type then
  354.             tagged_out_memory.extend('#');
  355.             Current.to_pointer.append_in(tagged_out_memory);
  356.          end;
  357.          tagged_out_memory.extend('[');
  358.          fill_tagged_out_memory;
  359.          tagged_out_memory.extend(']');
  360.       end;
  361.    
  362.    frozen tagged_out_memory: STRING is
  363.       once
  364.          !!Result.make(1024);
  365.       end;
  366.    
  367.    fill_tagged_out_memory is
  368.          -- Append a viewable information in `tagged_out_memory' in 
  369.          -- order to affect the behavior of `out', `tagged_out', etc.
  370.       do
  371.          -- Should be an external "SmallEiffel" to provide a default 
  372.          -- view of Current contents (not yet implemented).
  373.       end;
  374.    
  375. feature -- Basic named file handling :
  376.  
  377.    frozen file_tools: FILE_TOOLS is
  378.       once
  379.       end;
  380.    
  381.    file_exists(path: STRING): BOOLEAN is
  382.          -- True if `path' is an existing readable file.
  383.       require
  384.          path /= Void
  385.       do
  386.          Result := file_tools.is_readable(path);
  387.       end;
  388.    
  389.    remove_file(path: STRING) is
  390.       require
  391.          path /= Void;
  392.       do
  393.          file_tools.delete(path);
  394.       end;
  395.    
  396.    rename_file(old_path, new_path: STRING) is
  397.       require
  398.          old_path /= Void;
  399.          new_path /= Void
  400.       do
  401.          file_tools.rename_to(old_path,new_path);
  402.       end;
  403.  
  404. feature -- Access to command-line arguments :
  405.    
  406.    argument_count: INTEGER is
  407.          -- Number of arguments given to command that started
  408.          -- system execution (command name does not count).
  409.       do
  410.          Result := command_arguments.upper;
  411.       ensure
  412.          Result >= 0;
  413.       end;
  414.    
  415.    argument(i: INTEGER): STRING is
  416.          -- `i' th argument of command that started system execution 
  417.          -- Gives the command name if `i' is 0.
  418.       require
  419.          i >= 0;
  420.          i <= argument_count;
  421.       do
  422.          Result := command_arguments.item(i);
  423.       ensure
  424.          Result /= Void
  425.       end;
  426.  
  427.    frozen command_arguments: FIXED_ARRAY[STRING] is
  428.          -- Give acces to arguments command line including the
  429.          -- command name at index 0.
  430.       local
  431.          i: INTEGER;
  432.          arg: STRING;
  433.       once
  434.          from
  435.             i := se_argc;
  436.             !!Result.make(i);
  437.          until
  438.             i = 0
  439.          loop
  440.             i := i - 1;
  441.             arg := se_argv(i);
  442.             Result.put(arg,i);
  443.          end;
  444.       ensure
  445.          not Result.empty
  446.       end;
  447.    
  448.    get_environment_variable(name: STRING): STRING is
  449.          -- To get the value of a system environment variable
  450.          -- (like "PATH" on Unix for example).
  451.          -- Gives Void when system variable `name' is undefined.
  452.       require
  453.          name /= Void
  454.       local
  455.          p: POINTER;
  456.       do
  457.          p := name.to_external;
  458.          Result := se_getenv(p);
  459.       end;
  460.    
  461. feature -- System calls and crashs :
  462.    
  463.    frozen crash is
  464.          -- Print Run Time Stack and then exit with `exit_failure_code'.
  465.       do
  466.          print_run_time_stack;
  467.          die_with_code(exit_failure_code);
  468.       end;
  469.  
  470.    frozen trace_switch(flag: BOOLEAN) is
  471.          -- May be used in combination with option "-trace" of
  472.          -- command `compile_to_c' (see compile_to_c.hlp for
  473.          -- details).
  474.       external "SmallEiffel"
  475.       end;
  476.  
  477.    system(system_command_line: STRING) is
  478.          -- To execute a `system_command_line' as for example, "ls -l" on UNIX.
  479.       local
  480.          p: POINTER;
  481.       do
  482.          p := system_command_line.to_external;
  483.          se_system(p);
  484.       end;
  485.    
  486.    frozen die_with_code(code:INTEGER) is
  487.          -- Terminate execution with exit status code `code'.
  488.          -- Do not print any message.
  489.          -- Note: you can use predefined `exit_success_code' or
  490.          -- `exit_failure_code' as well as another code you need.
  491.       external "SmallEiffel"
  492.       end;
  493.    
  494.    exit_success_code: INTEGER is 0;
  495.    
  496.    exit_failure_code: INTEGER is 1;
  497.    
  498. feature -- Maths constants :
  499.  
  500.    Pi    : DOUBLE is  3.1415926535897932384626; 
  501.        
  502.    Evalue: DOUBLE is  2.7182818284590452353602;
  503.      
  504.    Deg   : DOUBLE is 57.2957795130823208767981; -- Degrees/Radian
  505.      
  506.    Phi   : DOUBLE is  1.6180339887498948482045; -- Golden Ratio
  507.  
  508. feature -- Character names :
  509.  
  510.    Ctrl_a: CHARACTER is '%/1/';
  511.    Ctrl_b: CHARACTER is '%/2/';
  512.    Ctrl_c: CHARACTER is '%/3/';
  513.    Ctrl_d: CHARACTER is '%/4/';
  514.    Ctrl_e: CHARACTER is '%/5/';
  515.    Ctrl_f: CHARACTER is '%/6/';
  516.    Ctrl_g: CHARACTER is '%/7/';
  517.    Ch_bs : CHARACTER is '%/8/';
  518.    Ch_tab: CHARACTER is '%/9/';
  519.    Ctrl_j: CHARACTER is '%/10/';
  520.    Ctrl_k: CHARACTER is '%/11/';
  521.    Ctrl_l: CHARACTER is '%/12/';
  522.    Ctrl_m: CHARACTER is '%/13/';
  523.    Ctrl_n: CHARACTER is '%/14/';
  524.    Ctrl_o: CHARACTER is '%/15/';
  525.    Ctrl_p: CHARACTER is '%/16/';
  526.    Ctrl_q: CHARACTER is '%/17/';
  527.    Ctrl_r: CHARACTER is '%/18/';
  528.    Ctrl_s: CHARACTER is '%/19/';
  529.    Ctrl_t: CHARACTER is '%/20/';
  530.    Ctrl_u: CHARACTER is '%/21/';
  531.    Ctrl_v: CHARACTER is '%/22/';
  532.    Ctrl_w: CHARACTER is '%/23/';
  533.    Ctrl_x: CHARACTER is '%/24/';
  534.    Ctrl_y: CHARACTER is '%/25/';
  535.    Ctrl_z: CHARACTER is '%/26/';
  536.    Ch_del: CHARACTER is '%/63/';
  537.  
  538. feature -- Should not exist :
  539.    
  540.    not_yet_implemented is
  541.       do
  542.          std_error.put_string(
  543.           "Sorry, Some Feature is Not Yet Implemented.%N%
  544.            %Please, if you can write it by yourself and if you send me%N%
  545.            %the corresponding tested Eiffel code, I may put it in the%N% 
  546.            %standard library!%N%
  547.            %Many Thanks in advance.%N%  
  548.            %D.Colnet e-mail: colnet@loria.fr%N");
  549.          crash;
  550.        end;
  551.  
  552. feature -- For ELS Compatibility :
  553.  
  554.    id_object(id: INTEGER): ANY is
  555.          -- Object for which `object_id' has returned `id';
  556.          -- Void if none.
  557.       require
  558.          id /= 0;
  559.       do
  560.          Result := object_id_memory.item(id);
  561.       end;
  562.    
  563.    object_id: INTEGER is
  564.          -- Value identifying current reference object.
  565.       require
  566.          not is_expanded_type
  567.       do
  568.          Result := object_id_memory.fast_index_of(Current);
  569.          if Result > object_id_memory.upper then
  570.             object_id_memory.add_last(Current);
  571.          end;
  572.       end;
  573.    
  574. feature -- The Guru section :
  575.    
  576.    to_pointer: POINTER is
  577.          -- Explicit conversion of a reference into POINTER type.
  578.       require
  579.          not is_expanded_type
  580.       external "SmallEiffel"
  581.       end;
  582.  
  583.    frozen is_expanded_type: BOOLEAN is
  584.          -- Target is not evaluated (Statically computed).
  585.          -- Result is true if target static type is an expanded type.
  586.          -- Useful for formal generic type.
  587.       external "SmallEiffel"
  588.       end;
  589.    
  590.    frozen is_basic_expanded_type: BOOLEAN is
  591.          -- Target is not evaluated (Statically computed).
  592.          -- Result is true if target static type is one of the 
  593.          -- following types: BOOLEAN, CHARACTER, INTEGER, REAL,
  594.          -- DOUBLE or POINTER.
  595.       external "SmallEiffel"
  596.       ensure
  597.          Result implies is_expanded_type
  598.       end;
  599.    
  600.    frozen object_size: INTEGER is
  601.          -- Gives the size of the current object at first level 
  602.          -- only (pointed-to sub-object are not concerned).  
  603.          -- The result is given in number of CHARACTER.
  604.       external "SmallEiffel"
  605.       end;
  606.  
  607. feature {NONE} -- The Guru section :
  608.    
  609.    c_inline_h(c_code: STRING) is
  610.          -- Target must be Current and `c_code' must be a manifest
  611.          -- string. Write `c_code' in the heading C file.
  612.       external "SmallEiffel"
  613.       end;
  614.  
  615.    c_inline_c(c_code: STRING) is
  616.          -- Target must be Current and `c_code' must be a manifest
  617.          -- string. Write `c_code' in the stream at current position.
  618.       external "SmallEiffel"
  619.       end;
  620.  
  621. feature {NONE} -- Implementation of GENERAL (do not use directly) :
  622.       
  623.    object_id_memory: ARRAY[ANY] is
  624.          -- For a portable implementation of `id_object'/`object_id'.
  625.          -- Note: I think that the pair `id_object'/`object_id' is
  626.          -- a stupid one. It should be removed.
  627.       once
  628.          !!Result.with_capacity(256,1);
  629.       end;
  630.  
  631.    print_run_time_stack is
  632.          -- Prints the run time stack.
  633.          -- The result depends both on compilation mode and 
  634.          -- target langage used (C or Java byte code).
  635.          -- Usually, in mode -boost, no information is printed.
  636.       external "SmallEiffel"
  637.       end;
  638.  
  639.    se_argc: INTEGER is
  640.          -- To implement `command_arguments'
  641.       external "SmallEiffel"
  642.       end;
  643.  
  644.    se_argv(i: INTEGER): STRING is
  645.          -- To implement `command_arguments'
  646.       external "SmallEiffel"
  647.       end;
  648.  
  649.    se_getenv(environment_variable: POINTER): STRING is
  650.          -- To implement `get_environment_variable'.
  651.       external "SmallEiffel"
  652.       end;
  653.       
  654.    se_system(system_command_line: POINTER) is
  655.       external "SmallEiffel"
  656.       end;
  657.  
  658. feature -- Implementation of GENERAL (do not use directly) :
  659.       
  660.    frozen se_assigned_from(other: GENERAL): BOOLEAN is
  661.          -- To implement `conforms_to' (must only be called inside
  662.          -- `conforms_to' because of VJRV rule).
  663.       require
  664.          not is_expanded_type
  665.       local
  666.          x: like Current;
  667.       do
  668.          x ?= other;
  669.          Result := x /= Void;
  670.       end;
  671.    
  672. end -- GENERAL
  673.  
  674.