Editing Cookbook

Jump to navigation Jump to search
Warning: You are not logged in. Your IP address will be publicly visible if you make any edits. If you log in or create an account, your edits will be attributed to your username, along with other benefits.

The edit can be undone. Please check the comparison below to verify that this is what you want to do, and then publish the changes below to finish undoing the edit.

Latest revision Your text
Line 17: Line 17:
This is a list of possible tests to check for features:
This is a list of possible tests to check for features:


<syntaxhighlight lang="Octave">
    ## support for 64 bit indexing
## support for 64 bit indexing
    sizemax () > intmax ("int32")
sizemax () > intmax ("int32")


## built with support for java
    ## built with support for java
usejava ("jvm")
    usejava ("jvm")


## Image IO with support for tif files
    ## Image IO with support for tif files
any (cellfun (@(x) ismember ("tif", x), {imformats.ext}))
    any (cellfun (@(x) ismember ("tif", x), {imformats.ext}))
## Image IO with support for png files
    ## Image IO with support for png files
any (cellfun (@(x) ismember ("png", x), {imformats.ext}))
    any (cellfun (@(x) ismember ("png", x), {imformats.ext}))
</syntaxhighlight>


=== Find if a package is installed ===
=== Find if a package is installed ===
Line 41: Line 39:
Use {{codeline|pkg ("list", pkg-name)}} like so:
Use {{codeline|pkg ("list", pkg-name)}} like so:


<syntaxhighlight lang="Octave">
if (! isempty (pkg ("list", "foo")))
if (! isempty (pkg ("list", "foo")))
  ## use functions from package foo, the prefered way
  ## use functions from package foo, the preferred way
elseif (! isempty (pkg ("list", "bar")))
elseif (! isempty (pkg ("list", "bar")))
  ## use functions from package bar, not so optimal
  ## use functions from package bar, not so optimal
else
else
  ## default case
  ## default case
endif
endif
</syntaxhighlight>


==== Discussion ====
==== Discussion ====
Line 62: Line 58:
then you might as well not catch it in the first place.
then you might as well not catch it in the first place.


<syntaxhighlight lang="Octave">
## This contraption doesn't add anything.  If 'pkg load' fails, it
## This contraption doesn't add anything.  If 'pkg load' fails, it
## will already give an error message to the user.
## will already give an error message to the user.
try
try
  pkg load foo;
  pkg load foo;
catch
catch
  error ("failed to load foo: %s", lasterr ());
  error ("failed to load foo: %s", lasterr ());
end_try_catch
end_try_catch


## Again, doesn't add anything.  The failure of 'pkg load' is enough
## Again, doesn't add anything.  The failure of 'pkg load' is enough
if (isempty (pkg ("list", "foo")))
if (isempty (pkg ("list", "foo")))
  error ("program: package foo is not installed");
  error ("program: package foo is not installed");
endif
endif
</syntaxhighlight>


Beware that an installed package is not always a guarantee that a function
Beware that an installed package is not always a guarantee that a function
Line 101: Line 95:


== Structures ==
== Structures ==
=== Retrieve a field value from all entries in a struct array ===
=== Retrieve a field value from all entries in a struct array ===
==== Problem ====
==== Problem ====
You have a struct array with multiple fields, and you want to access the value from a specific field from all elements. For example, you want to return the age from all patients in the following case:
You have a struct array with multiple fields, and you want to access the value from a specific field from all elements. For example, you want to return the age from all patients in the following case:


<syntaxhighlight lang="Octave">
  samples = struct ("patient", {"Bob", "Kevin", "Bob" , "Andrew"},
samples = struct ("patient", {"Bob", "Kevin", "Bob" , "Andrew"},
                    "age",    { 45  ,  52    ,  45  ,  23    },
                  "age",    { 45  ,  52    ,  45  ,  23    },
                    "protein", {"H2B", "CDK2" , "CDK2", "Tip60" },
                  "protein", {"H2B", "CDK2" , "CDK2", "Tip60" },
                    "tube"  , { 3  ,  5    ,  2    ,  18    }
                  "tube"  , { 3  ,  5    ,  2    ,  18    }
                    );
                  );
</syntaxhighlight>


==== Solution ====
==== Solution ====
Indexing the struct returns a comma separated list so use them to create a matrix.
Indexing the struct returns a comma separated list so use them to create a matrix.


<syntaxhighlight lang="Octave">
  [samples(:).age]
[samples(:).age]
</syntaxhighlight>


This however does not keep the original structure of the data, instead returning all values in a single column. To fix this, use {{Codeline|reshape()}}.
This however does not keep the original structure of the data, instead returning all values in a single column. To fix this, use {{Codeline|reshape()}}.


<syntaxhighlight lang="Octave">
  reshape ([samples(:).age], size (samples))
reshape ([samples(:).age], size (samples))
</syntaxhighlight>


==== Discussion ====
==== Discussion ====
Returning all values in a comma separated lists allows you to make anything out of them. If numbers are expected, create a matrix by enclosing them in square brackets. But if strings are to be expected, a cell array can also be easily generated with curly brackets


Returning all values in a comma separated lists allows you to make anything out of them.
  {samples(:).patient}
If numbers are expected, create a matrix by enclosing them in square brackets.
But if strings are to be expected, a cell array can also be easily generated with curly brackets
 
<syntaxhighlight lang="Octave">
{samples(:).patient}
</syntaxhighlight>


You are also not limited to return all elements, you may use logical indexing from other fields to get values from the others:
You are also not limited to return all elements, you may use logical indexing from other fields to get values from the others:


<syntaxhighlight lang="Octave">
  [samples([samples(:).age] > 34).tube]                ## return tube numbers from all samples from patients older than 34
[samples([samples(:).age] > 34).tube]                ## return tube numbers from all samples from patients older than 34
  [samples(strcmp({samples(:).protein}, "CDK2")).tube]  ## return all tube numbers for protein CDK2
[samples(strcmp({samples(:).protein}, "CDK2")).tube]  ## return all tube numbers for protein CDK2
</syntaxhighlight>


== Array manipulation ==
== Array manipulation ==
Line 152: Line 130:
==== Problem ====
==== Problem ====


For an array {{Codeline|A}} with arbitrary number of dimensions, select, for example, the first column.
For an array {{Codeline|A}} with arbitrary number of dimensions, select, for example, the first column. This would be {{Codeline|A(:, 1)}} if {{Codeline|A}} was 2-D, {{Codeline|A(:, 1, :)}} if {{Codeline|A}} was 3-D, and so on.
This would be {{Codeline|A(:, 1)}} if {{Codeline|A}} was 2-D, {{Codeline|A(:, 1, :)}} if {{Codeline|A}} was 3-D, and so on.


==== Solution ====
==== Solution ====


One possibility is to use {{manual|subsref}} with the input {{Codeline|idx}} created dynamically with {{manual|repelems}} to have the right number of dimensions.
One possibility is to use {{Codeline|subsref}} with the input {{Codeline|idx}} created dynamically with {{Codeline|repelems}} to have the right number of dimensions. This can be written as a function:
This can be written as a function:


<syntaxhighlight lang="Octave">
 
{{Code||<syntaxhighlight lang="octave" style="font-size:13px">
function [B]= array_slice (A,k,d)
function [B]= array_slice (A,k,d)
#return the k-th slice (row, column...) of A, with d specifying the dimension to slice on
#return the k-th slice (row, column...) of A, with d specifying the dimension to slice on
Line 179: Line 156:
%! A=rand(2, 3, 4, 5, 6);
%! A=rand(2, 3, 4, 5, 6);
%!assert (array_slice (A,2,3), A(:, :, 2, :, :))
%!assert (array_slice (A,2,3), A(:, :, 2, :, :))
</syntaxhighlight>
</syntaxhighlight>}}


To remove the singleton dimension {{Codeline|d}} from the result {{Codeline|B}}, use  
To remove the singleton dimension {{Codeline|d}} from the result {{Codeline|B}}, use  
 
{{Code||<syntaxhighlight lang="octave" style="font-size:13px">
<syntaxhighlight lang="Octave">
B = reshape(B, [size(B)([1:d-1 d+1:end])]);
B = reshape(B, [size(B)([1:d-1 d+1:end])]);
</syntaxhighlight>
</syntaxhighlight>}}


== Input/output ==
== Input/output ==
=== Display matched elements from different arrays ===
=== Display matched elements from different arrays ===
==== Problem ====
==== Problem ====
You have two, or more, arrays with paired elements and want to print out a string about them. For example:
You have two, or more, arrays with paired elements and want to print out a string about them. For example:


<syntaxhighlight lang="Octave">
    keys  = {"human",  "mouse", "chicken"};
keys  = {"human",  "mouse", "chicken"};
    values = [ 64        72      70      ];
values = [ 64        72      70      ];
</syntaxhighlight>


and you want to display:
and you want to display:


Calculated human genome GC content is 64%
    Calculated human genome GC content is 64%
Calculated mouse genome GC content is 72%
    Calculated mouse genome GC content is 72%
Calculated chicken genome GC content is 70%
    Calculated chicken genome GC content is 70%


==== Solution ====
==== Solution ====
Make a two rows cell array, with each paired data in a column and supply a cs-list to printf


Make a two rows cell array, with each paired data in a column and supply a cs-list to {{manual|printf}}
    values = num2cell (values);
 
    new    = {keys{:}; values{:}};
<syntaxhighlight lang="Octave">
    printf ("Calculated %s genome GC content is %i%%\n", new{:})
values = num2cell (values);
new    = {keys{:}; values{:}};
printf ("Calculated %s genome GC content is %i%%\n", new{:})
</syntaxhighlight>


or in a single line:
or in a single line:
 
    printf ("Calculated %s genome GC content is %i%%\n", {keys{:}; num2cell(values){:}}{:})
<syntaxhighlight lang="Octave">
   
printf ("Calculated %s genome GC content is %i%%\n", {keys{:}; num2cell(values){:}}{:})
</syntaxhighlight>   


==== Discussion ====
==== Discussion ====
{{Codeline|printf}} and family do not accept cell arrays as values. However, they keep repeating the template given as long as it has enough arguments to keep going. As such, the trick is on supplying a cs-list of elements which can be done by using a cell array and index it with {{Codeline|<nowiki>{}</nowiki>}}.


{{manual|printf}} and family do not accept cell arrays as values.
Since values are stored in column-major order, paired values need to be on the same column. A new row of data can then be added later with {{Codeline|new(end+1,:) <nowiki>= {"Andrew", "Bob", "Kevin"}</nowiki>}}. Note that normal brackets are now being used for indexing.
However, they keep repeating the template given as long as it has enough arguments to keep going.
As such, the trick is on supplying a cs-list of elements which can be done by using a cell array and index it with <code>{}</code>.
 
Since values are stored in column-major order, paired values need to be on the same column.
A new row of data can then be added later with
 
<syntaxhighlight lang="Octave">
new(end+1,:) = {"Andrew", "Bob", "Kevin"};
</syntaxhighlight>
 
Note that normal brackets are now being used for indexing.


=== Swap values ===
=== Swap values ===
If you want to exchange the value between two variables without creating a dummy one, you can simply do:
If you want to exchange the value between two variables without creating a dummy one, you can simply do:


<syntaxhighlight lang="Octave">
{{Code|Swap values without dummy variable|<syntaxhighlight lang="octave" style="font-size:13px">
[b,a] = deal (a,b);
[b,a] = deal (a,b);
</syntaxhighlight>
</syntaxhighlight>}}


=== Collect all output arguments of a function ===
=== Collect all output arguments of a function ===
If you have a function that returns several values, e.g.  
If you have a function that returns several values, e.g.  


<syntaxhighlight lang="Octave">
{{Code||<syntaxhighlight lang="octave" style="font-size:13px">
function [a b c]= myfunc ()
function [a b c]= myfunc ()
   [a,b,c] = deal (1,2,3);  
   [a,b,c] = deal (1,2,3);  
endfunction
endfunction
</syntaxhighlight>
</syntaxhighlight>}}


and you want to collect them all into a single cell (similarly to Python's zip() function) you can do:
and you want to collect them all into a single cell (similarly to Python's zip() function) you can do:


<syntaxhighlight lang="Octave">
{{Code|Collect multiple output arguments|<syntaxhighlight lang="octave" style="font-size:13px">
outargs = nthargout (1:3, @myfunc)
outargs = nthargout (1:3, @myfunc)
</syntaxhighlight>
</syntaxhighlight>}}


=== Create a text table with fprintf===
=== Create a text table with fprintf===
(a.k.a. A funny formatting trick with fprintf found by chance)


Imagine that you want to create a text table with {{manual|fprintf}} with 2 columns of 15 characters width and both right justified.
Imagine that you want to create a text table with fprintf with 2 columns of 15 characters width and both right justified. How to do this thing?
How to do this thing?


That's easy:
That's easy:


If the variable Text is a cell array of strings (of length < 15) with two columns and a certain number of rows, simply type for the k-th row of Text
If the variable Text is a cell array of strings (of length <15) with two columns and a certain number of rows, simply type for the kth row of Text
 
{{Code||<syntaxhighlight lang="octave" style="font-size:13px">
<syntaxhighlight lang="Octave">
fprintf('%15.15s | %15.15s\n', Text{k,1}, Text{k,2});
fprintf('%15.15s | %15.15s\n', Text{k,1}, Text{k,2});
</syntaxhighlight>}}
</syntaxhighlight>
The syntax '%<n>.<m>s' allocates '<n>' places to write chars and display the '<m>' first characters of the string to display.
 
The syntax <code>%<n>.<m>s</code> allocates <code>n</code> places to write chars and display the <code>m</code> first characters of the string to display.


Example:
Example:
 
{{Code|Example create a text table with fprintf|<syntaxhighlight lang="octave" style="font-size:13px">
<syntaxhighlight lang="Octave">
octave:1> Text={'Hello','World'};
Text = {"Hello", "World"};
octave:2> fprintf('%15.15s | %15.15s\n', Text{1,1}, Text{1,2})
fprintf('%15.15s | %15.15s\n', Text{1,1}, Text{1,2})
</syntaxhighlight>
 
           Hello |          World
           Hello |          World
</syntaxhighlight>}}


===Load comma separated values (*.csv) files===
===Load comma separated values (*.csv) files===
Please note that all contributions to Octave may be edited, altered, or removed by other contributors. If you do not want your writing to be edited mercilessly, then do not submit it here.
You are also promising us that you wrote this yourself, or copied it from a public domain or similar free resource (see Octave:Copyrights for details). Do not submit copyrighted work without permission!

To edit this page, please answer the question that appears below (more info):

Cancel Editing help (opens in new window)