GNU Octave 7.1.0
A high-level interpreted language, primarily intended for numerical computations, mostly compatible with Matlab
op-mi.cc
Go to the documentation of this file.
1////////////////////////////////////////////////////////////////////////
2//
3// Copyright (C) 2020-2022 The Octave Project Developers
4//
5// See the file COPYRIGHT.md in the top-level directory of this
6// distribution or <https://octave.org/copyright/>.
7//
8// This file is part of Octave.
9//
10// Octave is free software: you can redistribute it and/or modify it
11// under the terms of the GNU General Public License as published by
12// the Free Software Foundation, either version 3 of the License, or
13// (at your option) any later version.
14//
15// Octave is distributed in the hope that it will be useful, but
16// WITHOUT ANY WARRANTY; without even the implied warranty of
17// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18// GNU General Public License for more details.
19//
20// You should have received a copy of the GNU General Public License
21// along with Octave; see the file COPYING. If not, see
22// <https://www.gnu.org/licenses/>.
23//
24////////////////////////////////////////////////////////////////////////
25
26#if defined (HAVE_CONFIG_H)
27# include "config.h"
28#endif
29
30#include <iostream>
31
32#include "errwarn.h"
33#include "ops.h"
34#include "ov-magic-int.h"
35#include "ov-typeinfo.h"
36#include "ov.h"
37
38OCTAVE_NAMESPACE_BEGIN
39
40// Magic integer unary ops. Only + and - are allowed so that
41// expressions like
42//
43// int64 (-9007199254740994)
44//
45// produce proper int64 constants.
46
47static octave_value
49{
50 const octave_magic_uint& v = dynamic_cast<const octave_magic_uint&> (a);
51 // no-op.
52 // FIXME: but can we do this just by incrementing the reference count?
53 return octave_value (v.clone ());
54}
55
56static octave_value
58{
59 const octave_magic_uint& v = dynamic_cast<const octave_magic_uint&> (a);
60
61 // We are storing a uint64 value, so some fakery is needed here.
62 // Is there a better way?
63
64 // FIXME: Maybe there should also be octave_magic_int::as_TYPE_value
65 // functions?
66 octave_uint64 val (v.scalar_ref ());
67
68 uint64_t ival = val.value ();
69
70 static const uint64_t max_val
71 = static_cast<uint64_t> (std::numeric_limits<int64_t>::max ());
72
73 static const uint64_t max_val_p1 = max_val + 1;
74
75 if (ival <= max_val)
76 {
77 int64_t signed_ival = ival;
78 return octave_value (new octave_magic_int (-signed_ival));
79 }
80
81 if (ival == max_val_p1)
82 {
83 // Correctly capture intmin. For example, negating uint8(128)
84 // should return int8(-128) but converting directly to int8 and
85 // negating will not return the correct result.
86
87 static const int64_t min_signed_ival
89
90 return octave_value (new octave_magic_int (min_signed_ival));
91 }
92
93 return octave_value (-static_cast<double> (ival));
94}
95
96static octave_value
98{
99 const octave_magic_int& v = dynamic_cast<const octave_magic_int&> (a);
100 // no-op.
101 // FIXME: but can we do this just by incrementing the reference count?
102 return octave_value (v.clone ());
103}
104
105static octave_value
107{
108 const octave_magic_int& v = dynamic_cast<const octave_magic_int&> (a);
109
110 // FIXME: Maybe there should also be octave_magic_int::as_TYPE_value
111 // functions?
112 octave_int64 val (v.scalar_ref ());
113
114 return octave_value (new octave_magic_int (-val));
115}
116
117void
118install_mi_ops (octave::type_info& ti)
119{
120 INSTALL_UNOP_TI (ti, op_uplus, octave_magic_uint, unsigned_uplus);
121 INSTALL_UNOP_TI (ti, op_uminus, octave_magic_uint, unsigned_uminus);
122
123 INSTALL_UNOP_TI (ti, op_uplus, octave_magic_int, signed_uplus);
124 INSTALL_UNOP_TI (ti, op_uminus, octave_magic_int, signed_uminus);
125}
126
127OCTAVE_NAMESPACE_END
charNDArray max(char d, const charNDArray &m)
Definition: chNDArray.cc:230
charNDArray min(char d, const charNDArray &m)
Definition: chNDArray.cc:207
const T & scalar_ref(void) const
Definition: ov-magic-int.h:72
T value(void) const
Definition: oct-inttypes.h:830
octave_base_value * clone(void) const
Definition: ov-magic-int.h:316
octave_base_value * clone(void) const
Definition: ov-magic-int.h:290
return octave_value(v1.char_array_value() . concat(v2.char_array_value(), ra_idx),((a1.is_sq_string()||a2.is_sq_string()) ? '\'' :'"'))
static octave_value oct_unop_unsigned_uminus(const octave_base_value &a)
Definition: op-mi.cc:57
static octave_value oct_unop_signed_uplus(const octave_base_value &a)
Definition: op-mi.cc:97
static OCTAVE_NAMESPACE_BEGIN octave_value oct_unop_unsigned_uplus(const octave_base_value &a)
Definition: op-mi.cc:48
void install_mi_ops(octave::type_info &ti)
Definition: op-mi.cc:118
static octave_value oct_unop_signed_uminus(const octave_base_value &a)
Definition: op-mi.cc:106
#define INSTALL_UNOP_TI(ti, op, t, f)
Definition: ops.h:45
octave_value op_uplus(const octave_value &a)
Definition: ov.h:1836
octave_value op_uminus(const octave_value &a)
Definition: ov.h:1837